H3xano/dahua-rpc-api

GitHub: H3xano/dahua-rpc-api

大华IP摄像机和NVR的JSON-RPC API完整逆向文档,涵盖275个以上的方法、认证机制和调用规范。

Stars: 1 | Forks: 0

# 大华 IP 摄像机 / NVR JSON-RPC API 参考 [![许可证: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT) [![方法](https://img.shields.io/badge/methods-275%2B-blue.svg)](https://github.com/H3xano/dahua-rpc-api) 大华专有 JSON-RPC API 的完整文档,已从设备内部 JavaScript 源文件(`rpc.js`、`rpcBase.js`、`rpcLogin.js`)逆向工程得出。 ## 架构 大华设备使用专有的 **JSON-RPC 2.0 over HTTP** 协议。 | 属性 | 值 | |---|---| | HTTP 方法 | `POST` | | Content-Type | `application/json` | | 认证端点 | `/RPC2_Login` | | 命令端点 | `/RPC2` | | 未认证端点 | `/OutsideCmd`(密码重置等) | ### 标准负载结构 每个请求都遵循此精确的 JSON 结构(来自 `rpcBase.js`): ``` { "method": "moduleName.actionName", "params": { "key": "value" }, "id": 1, "session": "YOUR_SESSION_ID" } ``` | 字段 | 描述 | |---|---| | `method` | 要执行的操作,例如 `ptz.start` | | `params` | 参数对象。如果没有请发送 `null` | | `id` | 整数,每次请求递增 1 | | `session` | 登录会话令牌 | ### 端点 | 端点 | 用途 | |---|---| | `/RPC2_Login` | 仅用于认证(`global.login`) | | `/RPC2` | 所有标准 RPC 命令 | | `/OutsideCmd` | 未认证命令(密码重置) | ## 认证(两步挑战-响应握手) 大华从不以明文发送密码。使用来自 `rpcLogin.js` 的挑战-响应机制。 ### 步骤 1:挑战 使用**空**密码发送登录请求到 `/RPC2_Login`: ``` { "method": "global.login", "params": { "userName": "admin", "password": "", "clientType": "Web3.0" }, "id": 1 } ``` **响应:** 摄像机返回错误 `Code 268632079`,但在 `params` 中包含关键令牌: - `realm` — 例如 "Login to 4X02345PAJ9A82F" - `random` — 此会话的随机字符串 - `session` — 临时会话 ID ### 步骤 2:响应 使用 `rpcLogin.js` 中 `k.getAuth` 的公式在本地哈希密码: ``` Hash1 = MD5(username + ":" + realm + ":" + plain_password) Hash2 = MD5(username + ":" + random + ":" + Hash1) ``` 发送第二个请求到 `/RPC2_Login`,使用 `Hash2` 作为密码和临时 `session`: ``` { "method": "global.login", "params": { "userName": "admin", "password": "", "clientType": "Web3.0" }, "id": 2, "session": "" } ``` **成功响应:** `{"result": true, "session": ""}` ### 加密模式 | 模式 | 公式 | 来源 | |---|---|---| | Basic | `Base64(username + ":" + password)` | `rpcLogin.js` | | Default | `MD5(user:random:MD5(user:realm:pass))` | `rpcLogin.js` | ## 特殊机制 ### 多调用(批处理) 使用 `system.multicall` 在一个 HTTP 请求中执行多个命令: ``` { "method": "system.multicall", "params": [ {"method": "ptz.start", "params": {"code": "Right", "arg1": 4, "arg2": 0, "arg3": 0, "arg4": 0, "channel": 0}, "id": 2}, {"method": "ptz.stop", "params": {"code": "Right", "arg1": 4, "arg2": 0, "arg3": 0, "arg4": 0, "channel": 0}, "id": 3} ], "id": 4, "session": "" } ``` ### 安全调用(`system.multiSec`) 敏感命令(添加用户、修改密码、网络配置如 PPPoE/VPN/DDNS/Email)使用 `system.multiSec`。UI 在发送前使用 RSA(来自摄像机的公钥)或 AES-128/256 加密 `params`。 ### 发现命令 `system.listMethod` 返回您的固件支持的每个 RPC 方法: ``` curl -X POST http:///RPC2 \ -H "Content-Type: application/json" \ -d '{"method":"system.listMethod","params":null,"id":1,"session":""}' ``` ## 会话生命周期 - 每约 60 秒发送 `global.keepAlive` 以防止会话过期 - 会话无效 = 错误代码 `287637504` - 失效时,UI 通过 `rpcLogin.js` 的 keepalive 处理器自动重连 - 连续 5 次 keepalive 失败后,UI 重新加载 ## 最佳实践 1. **先检查能力:** UI 使用 `jsCore/ability.js` 在显示按钮前询问摄像机是否支持某功能。不要假设命令有效(例如 `ptz.start` 在固定半球摄像头上会失败)。 2. **Keep-alive:** 空闲时会话会过期。每约 60 秒发送 `global.keepAlive`。 3. **加密配置:** NVR 和新型号 IPC 加密网络配置。`configManager.getConfig` 获取 `"PPPoE"`、`"DDNS"`、`"VPN"`、`"Email"` 需要使用 AES 的 `system.multiSec`。基本设置(如视频编码等)使用标准 RPC。 ## 模块参考 | 模块 | 文件 | |---|---| | 核心端点与负载 | `modules/00-core-endpoints.md` | | 认证与会话 | `modules/01-authentication.md` | | 系统与 MagicBox | `modules/02-system-magicbox.md` | | 配置管理器 | `modules/03-configuration.md` | | 云台与镜头控制 | `modules/04-ptz-lens.md` | | 视频、音频与编码 | `modules/05-video-audio-encoding.md` | | 报警与事件 | `modules/06-alarms-events.md` | | IVS、分析与人脸 | `modules/07-ivs-analytics-faces.md` | | 存储与文件 | `modules/08-storage-files.md` | | 网络与连接 | `modules/09-network.md` | | 安全与用户 | `modules/10-security-users.md` | | 热成像与传感器 | `modules/11-thermography-sensors.md` | | 维护与升级 | `modules/12-maintenance-upgrade.md` | ## Python 客户端 有关可工作的 Python 登录 + 发现脚本,请参阅 `reference/dahua_rpc_client.py`。
标签:API安全, API文档, ASN解析, CMS安全, Dahua, HTTP协议, IP Camera, JavaScript, JSON-RPC, JSON输出, NVR, 事件响应, 云资产清单, 协议分析, 固件分析, 挑战响应, 摄像头安全, 权限提升, 物联网安全, 网络安全, 认证机制, 设备控制, 逆向工具, 逆向工程, 隐私保护