feat: 初始化小米 IoT (MIoT) 智能家居 Go 库

- 实现 MIoT 客户端核心功能(MQTT 连接、设备管理、属性读写)
- 支持云端 API 调用与局域网设备发现(mDNS)
- 集成国际化(i18n)多语言支持
- 添加 MIoT 设备规约解析器(spec_parser)
- 包含单元测试与使用示例
This commit is contained in:
2026-06-28 22:05:49 +08:00
parent ac442812b4
commit 3a44cb9e6a
118 changed files with 31630 additions and 0 deletions
+284
View File
@@ -0,0 +1,284 @@
# 01 - miot_client.py 移植计划
## 概览
| 项目 | 内容 |
|------|------|
| **Python 文件** | `py-miot/miot_client.py` (837行) |
| **Go 文件** | `go-miot/miot_client.go` + `miot_client_api.go` + `miot_client_prop.go` + `miot_client_sub.go` |
| **状态** | ⚠️ 部分实现 |
| **优先级** | 🔴 P0 |
| **预计工作量** | 8-12 小时 |
## Python 版本分析
### 核心类
#### MIoTClient
**位置**:第 31-837 行
**主要职责**:
- 小米 IoT 设备的主客户端类
- 管理设备列表、属性刷新、命令发送
- 协调多个子模块(OAuth、Cloud、MIPS)
**核心方法**:
| 方法名 | 行号 | 功能 | Go 状态 |
|--------|------|------|---------|
| `__init__` | 31 | 初始化客户端,加载配置 | ✅ 已完成 |
| `load_config` | 47 | 加载配置文件 | ✅ 已完成 |
| `save_config` | 68 | 保存配置文件 | ✅ 已完成 |
| `discover_devices` | 89 | 发现设备(从云端或本地) | ⚠️ 部分实现 |
| `get_devices` | 125 | 获取设备列表 | ✅ 已完成 |
| `get_device` | 142 | 根据 DID 获取单个设备 | ✅ 已完成 |
| `refresh_devices` | 163 | 刷新设备列表(从云端) | ⚠️ 部分实现 |
| `refresh_properties` | 201 | 批量刷新设备属性 | ⚠️ 部分实现 |
| `send_command` | 267 | 发送控制命令 | ⚠️ 部分实现 |
| `subscribe_prop` | 345 | 订阅属性变化 | ❌ 缺失 |
| `unsubscribe_prop` | 389 | 取消订阅属性变化 | ❌ 缺失 |
| `start_monitor` | 423 | 启动属性监控线程 | ❌ 缺失 |
| `stop_monitor` | 467 | 停止属性监控线程 | ❌ 缺失 |
| `poll_devices` | 501 | 轮询设备状态 | ❌ 缺失 |
| `call_action` | 567 | 调用设备动作(如开启、关闭) | ⚠️ 部分实现 |
| `get_device_prop` | 623 | 获取设备属性值 | ✅ 已完成 |
| `set_device_prop` | 659 | 设置设备属性值 | ✅ 已完成 |
| `run_mips_script` | 721 | 运行 MIPS 脚本 | ❌ 缺失 |
| `close` | 789 | 关闭客户端,释放资源 | ⚠️ 部分实现 |
### 辅助函数
| 函数名 | 行号 | 功能 | Go 状态 |
|--------|------|------|---------|
| `load_token_from_env` | 812 | 从环境变量加载 token | ❌ 缺失 |
| `parse_device_list` | 826 | 解析设备列表 JSON | ✅ 已完成 |
## Go 版本现状
### 已实现的文件结构
```
go-miot/
├── miot_client.go # 主客户端类(对应 Python 的 MIoTClient)
├── miot_client_api.go # API 调用方法(对应 Python 的网络请求)
├── miot_client_prop.go # 属性相关方法(对应 Python 的 refresh_properties 等)
├── miot_client_sub.go # 订阅相关方法(对应 Python 的 subscribe_prop 等)
└── miot_device.go # 设备类(对应 Python 的 MIoTDevice)
```
### 缺失的功能
#### 1. 设备发现 (`discover_devices`)
**Python 实现**:
```python
def discover_devices(self, source: str = "cloud"):
"""发现设备"""
if source == "cloud":
return self.refresh_devices()
elif source == "lan":
return self._discover_lan_devices()
else:
raise ValueError(f"Unknown source: {source}")
```
**Go 缺失**:
- ❌ LAN 设备发现(需要 `miot_lan.py`)
- ⚠️ 云端设备发现已部分实现
#### 2. 属性订阅系统 (`subscribe_prop`, `unsubscribe_prop`)
**Python 实现**:
- 使用回调机制
- 支持多设备、多属性订阅
- 后台线程轮询
**Go 缺失**:
- ❌ 完整的订阅系统
- ❌ 回调机制
- ❌ 后台轮询线程
#### 3. 属性监控 (`start_monitor`, `stop_monitor`)
**Python 实现**:
- 启动后台线程
- 定期轮询订阅的属性
- 触发回调
**Go 缺失**:
- ❌ 后台 goroutine 管理
- ❌ 定时轮询
- ❌ 回调触发
#### 4. MIPS 脚本支持 (`run_mips_script`)
**Python 实现**:
- 调用 MIPS 客户端
- 执行自动化脚本
**Go 缺失**:
- ❌ MIPS 客户端集成
- ❌ 脚本执行接口
## 移植建议
### 第一批任务(核心功能)
1. **补全 `discover_devices`** (2小时)
- 实现 LAN 设备发现接口(占位)
- 统一云端和本地发现的返回格式
2. **实现属性订阅系统** (4小时)
- 设计回调接口(`PropertyChangeCallback`)
- 实现 `SubscribeProp` 方法
- 实现 `UnsubscribeProp` 方法
- 管理订阅列表
3. **实现属性监控** (3小时)
- 启动后台 goroutine
- 定时轮询订阅的属性
- 比较属性变化,触发回调
- 实现优雅停止
### 第二批任务(高级功能)
4. **MIPS 脚本支持** (2小时)
- 集成 MIPS 客户端
- 实现 `RunMipsScript` 方法
5. **环境变量支持** (1小时)
- 实现 `load_token_from_env`
- 支持从环境变量读取配置
## 技术难点
### 1. 并发安全
**问题**:Python 版本使用线程,Go 版本需要使用 goroutine
**建议**:
- 使用 `sync.RWMutex` 保护共享状态
- 使用 channel 进行 goroutine 通信
- 避免全局变量
### 2. 回调机制
**问题**:Python 使用函数回调,Go 需要使用接口或 channel
**建议**:
```go
// 方案 1:接口
type PropertyChangeCallback interface {
OnPropertyChange(device *MIoTDevice, prop *Property, oldValue, newValue interface{})
}
// 方案 2:函数类型
type PropertyChangeHandler func(device *MIoTDevice, prop *Property, oldValue, newValue interface{})
// 方案 3:Channel
type PropertyChangeEvent struct {
Device *MIoTDevice
Property *Property
OldValue interface{}
NewValue interface{}
}
var PropertyChangeChan = make(chan PropertyChangeEvent, 100)
```
### 3. 后台任务管理
**问题**:Python 使用 `threading.Thread`,Go 需要使用 goroutine 和 context
**建议**:
```go
type MIoTClient struct {
// ...
monitorCtx context.Context
monitorCancel context.CancelFunc
monitorWg sync.WaitGroup
}
func (c *MIoTClient) StartMonitor(interval time.Duration) error {
c.monitorCtx, c.monitorCancel = context.WithCancel(context.Background())
c.monitorWg.Add(1)
go func() {
defer c.monitorWg.Done()
ticker := time.NewTicker(interval)
defer ticker.Stop()
for {
select {
case <-c.monitorCtx.Done():
return
case <-ticker.C:
c.pollSubscribedProperties()
}
}
}()
return nil
}
```
## 测试计划
### 单元测试
1. **设备发现测试**
- 测试云端设备发现
- 测试本地设备发现(需要 mock)
2. **属性订阅测试**
- 测试订阅和取消订阅
- 测试回调触发
- 测试并发订阅
3. **属性监控测试**
- 测试启动和停止
- 测试定时轮询
- 测试优雅停止
### 集成测试
1. **端到端测试**
- 使用真实设备测试
- 测试完整流程:发现 → 订阅 → 监控 → 控制
## 依赖关系
| 依赖文件 | 关系 | 说明 |
|---------|------|------|
| `miot_device.py` | 强依赖 | 设备类 |
| `miot_cloud.py` | 强依赖 | 云端 API |
| `miot_oauth.py` | 强依赖 | OAuth 认证 |
| `miot_storage.py` | 强依赖 | 配置存储 |
| `miot_mips.py` | 弱依赖 | MIPS 脚本 |
| `miot_lan.py` | 弱依赖 | LAN 控制 |
## 移植优先级
| 任务 | 优先级 | 理由 |
|------|--------|------|
| 补全 `discover_devices` | 🔴 高 | 核心功能,影响设备发现 |
| 实现属性订阅 | 🔴 高 | 核心功能,影响实时监控 |
| 实现属性监控 | 🔴 高 | 核心功能,影响实时监控 |
| MIPS 脚本支持 | 🟡 中 | 高级功能,可选 |
| 环境变量支持 | 🟢 低 | 辅助功能,方便配置 |
## 进度跟踪
- [ ] 补全 `discover_devices` (预计 2小时)
- [ ] 实现属性订阅系统 (预计 4小时)
- [ ] 实现属性监控 (预计 3小时)
- [ ] MIPS 脚本支持 (预计 2小时)
- [ ] 环境变量支持 (预计 1小时)
- [ ] 单元测试 (预计 4小时)
- [ ] 集成测试 (预计 2小时)
**总计**:18小时
---
**创建时间**:2026-06-28
**最后更新**:2026-06-28
**负责人**:待定