Files
hawkbit/huaxu
lingwei.kong c191bd07ba
Some checks failed
Mark & close stale issues / stale (push) Has been cancelled
Vulnerability Scan / trivy-scan (1.0) (push) Has been cancelled
Vulnerability Scan / trivy-scan (master) (push) Has been cancelled
添加huaxuapi说明
2026-06-26 17:14:13 +08:00
..
2026-06-26 17:14:13 +08:00
2026-06-26 17:14:13 +08:00
2026-06-26 17:14:13 +08:00
2026-06-26 17:14:13 +08:00

Hawkbit DDI Client

轻量级纯 Python OTA 更新代理,零依赖(仅 Python 3 标准库),可在 Android adb shellLinux 主机上运行。

功能

功能 说明
轮询 GET /{tenant}/controller/v1/{controllerId} 查询部署任务,自动适配服务端建议的轮询间隔
断点下载 HTTP Range 请求实现断点续传,临时 .tmp 文件保留至下载完成
SHA256 校验 下载完成后自动与部署元数据中的哈希值比对
状态上报 完整状态链:downloaddownloadedproceedingclosed(success/failure)
设备 SN 检测 自动检测序列号Android ro.serialno → DMI product_serial/etc/machine-id → hostname
设备属性上报 首次连接自动上报设备属性osType, platform, hwRevision, kernel…供 Hawkbit target filter 匹配
认证 支持 GatewayTokenTargetToken,也支持从文件读取:--gateway-token @/etc/hawkbit/gateway.key
取消/确认 处理 cancelAction(取消任务)和 confirmationBaseheadless 自动确认)

设备属性上报

脚本在首次轮询时自动调用 PUT …/configData 上报以下属性:

属性 来源 示例
osType /system/build.prop 或 uname android / linux
platform platform.machine() aarch64 / x86_64
kernel os.uname().release 6.17.0-35-generic
hwRevision DMI product_name + product_version VMware Virtual Platform
manufacturer DMI sys_vendor 或 Android ro.product.manufacturer VMware, Inc.
hostname socket.gethostname() device-001
swVersion /etc/hawkbit/current_version(可选) V1.0.0.0

扩展属性:创建 /etc/hawkbit/device_attrs.json 添加自定义属性:

{"dept": "production", "region": "east", "owner": "team-a"}

这些属性在 Hawkbit 里就是 target 的 attributes管理员创建 target filter 时可以直接用:

属性 osType=android AND hwRevision=VMware  →  自动分配 V2.0 更新

## 快速开始

```bash
# 网关令牌,每 30 秒轮询
python3 ddi-client.py -u https://hawkbit.example.com -t DEFAULT --gateway-token s3cret -i 30

# 网关令牌从文件读取(生产推荐)
echo "s3cret" > /etc/hawkbit/gateway.key
chmod 600 /etc/hawkbit/gateway.key
python3 ddi-client.py -u https://hawkbit.example.com -t DEFAULT \
    --gateway-token @/etc/hawkbit/gateway.key -i 30

# 目标令牌,单次轮询
python3 ddi-client.py -u http://10.0.0.1:8080 -t DEFAULT --target-token tok --once

# 自定义设备 ID + 自定义属性文件,调试模式
python3 ddi-client.py -u https://hawkbit:8443 -t prod \
    --gateway-token @/etc/hawkbit/gateway.key \
    --controller-id edge-042 -d /data/ota -v

命令行参数

-u, --base-url           Hawkbit 服务端地址(必填)
-t, --tenant             租户名称,如 DEFAULT必填
--gateway-token          Gateway 安全令牌
--target-token           Target 安全令牌
--controller-id          控制器 ID默认自动检测设备序列号
-d, --download-dir       下载目录,默认 /tmp/hawkbit
-i, --polling-interval   轮询间隔(秒),默认 60可被服务端覆盖
--no-verify              跳过 SHA256 校验
--no-resume              禁用断点续传
--no-ssl-verify          禁用 TLS 证书验证(不安全)
--once                   仅轮询一次后退出
-v, --verbose            调试级日志
-h, --help               帮助信息

DDI API 流程

  ┌─────────┐     ① GET /{tenant}/controller/v1/{controllerId}     ┌──────────┐
  │         │ ────────────────────────────────────────────────────→ │          │
  │  设备   │     ←──── HAL links (deploymentBase / cancel / …)     │ Hawkbit  │
  │         │                                                       │  Server  │
  │         │     ② GET …/deploymentBase/{actionId}                 │          │
  │         │ ────────────────────────────────────────────────────→ │          │
  │         │     ←──── chunks[].artifacts[] (filename, SHA256,     │          │
  │         │            download URL)                              │          │
  │         │                                                       │          │
  │         │     ③ GET …/softwaremodules/{id}/artifacts/{file}     │          │
  │         │ ────────────────────────────────────────────────────→ │          │
  │         │     ←──── 二进制流(支持 Range 断点续传)                 │          │
  │         │                                                       │          │
  │         │     ④ POST …/deploymentBase/{actionId}/feedback       │          │
  │         │ ───── {execution, result, details} ────────────────→  │          │
  │         │     ←──── 200 OK                                      │          │
  └─────────┘                                                       └──────────┘

状态上报 JSON 格式

{
    "timestamp": 1750000000000,
    "status": {
        "execution": "download",
        "result": {
            "finished": "none"
        },
        "details": ["Starting download"]
    }
}
execution 值 含义 result.finished
download 开始下载 none
downloaded 下载完成 none
proceeding 安装中 none
closed 最终状态 success / failure
canceled 已取消 none
rejected 已拒绝 none

认证配置

Target Token推荐每设备独立令牌

在 Hawkbit Management API 中为目标设置 security token

curl -u admin:admin -X PUT \
  -H "Content-Type: application/json" \
  "http://<hawkbit>:9090/rest/v1/targets/<controllerId>" \
  -d '{"securityToken": "my-device-token"}'

启用租户级 TargetToken 认证:

curl -u admin:admin -X PUT \
  -H "Content-Type: application/json" \
  "http://<hawkbit>:9090/rest/v1/system/configs/authentication.targettoken.enabled" \
  -d '{"value": true}'

Gateway Token所有设备共享同一令牌

# 设置 token key
curl -u admin:admin -X PUT \
  -H "Content-Type: application/json" \
  "http://<hawkbit>:9090/rest/v1/system/configs/authentication.gatewaytoken.key" \
  -d '{"value": "my-gateway-key"}'

# 启用
curl -u admin:admin -X PUT \
  -H "Content-Type: application/json" \
  "http://<hawkbit>:9090/rest/v1/system/configs/authentication.gatewaytoken.enabled" \
  -d '{"value": true}'

设备 SN 检测优先级

优先级 来源 适用平台
1 getprop ro.serialno Android
2 /sys/class/dmi/id/product_serial Linux (x86)
3 /sys/devices/virtual/dmi/id/product_serial Linux (ARM / 嵌入式)
4 /etc/machine-id systemd Linux
5 socket.gethostname() 通用回退

安装钩子

下载完成后,脚本调用 _install(files, handling) 方法执行实际安装。默认实现仅做文件存在性检查,生产环境必须覆盖此方法

方式一:子类继承

from ddi_client import HawkbitDDIClient

class MyClient(HawkbitDDIClient):
    def _install(self, files, handling):
        import subprocess
        for f in files:
            subprocess.run(["unzip", "-o", f, "-d", "/data/ota"], check=True)
        return True

方式二Monkey-Patch

client = HawkbitDDIClient(...)
client._install = lambda files, h: do_my_install(files)

兼容性

  • Python ≥ 3.7
  • Android (adb shell, 需安装 Python)
  • Linux (x86_64 / aarch64 / armv7l)
  • macOS
  • Hawkbit DDI API v1

文件结构

ddi-client.py          # 脚本本体(单文件,可直接部署)

无其他依赖文件。