# xiaomi 封装层示例程序规划 > 状态:Completed | 版本:v1.0 | 日期:2026-06-28 | 完成日期:2026-06-29 --- ## 一、现状分析 ### 已有示例 | 文件 | 状态 | 问题 | |------|------|------| | `xiaomi/examples/main.go` | 存在(224 行) | 几乎全是 `fmt.Println` 伪代码,非可运行的完整示例 | ### 目标 对标 `ARCH_PLAN.md` v1.1 的最终形态,覆盖完整 API 面,每个示例独立可理解、贴近实战。 --- ## 二、示例架构 ``` xiaomi/examples/ ├── 01_user_home/ # 用户 + 家庭 + 房间信息 │ └── main.go ├── 02_device_list/ # 设备列表 + 过滤 │ └── main.go ├── 03_switch_control/ # 开关控制 │ └── main.go ├── 04_light_control/ # 灯光控制 │ └── main.go ├── 05_ac_control/ # 空调控制 │ └── main.go ├── 06_fan_cover/ # 风扇 + 窗帘控制 │ └── main.go ├── 07_prop_subscribe/ # 属性/事件/状态订阅 │ └── main.go ├── 08_adv_filter_classify/ # 高级过滤 + 分类 + 工厂 │ └── main.go ├── 09_spec_parser/ # SPEC 解析器独立使用(已有完整代码) │ └── main.go └── config/ # 共享配置模块(敏感信息统一管理) └── config.go ``` --- ## 三、各示例详述 ### 01_user_home — 用户/家庭/房间信息 **覆盖 API**: - `client.GetUserInfo(ctx)` → `*UserInfo` - `client.GetHomeList(ctx)` → `[]*HomeInfo`(含经纬度、地址) - `client.GetHome(ctx, homeID)` → `*HomeInfo` - `client.GetRooms(ctx, homeID)` → `[]*RoomInfo` - `client.GetRoomDevices(ctx, homeID, roomID)` → `[]string` **演示重点**: - context.WithTimeout 控制超时 - HomeInfo 的地里位置字段(CityID, Longitude, Latitude, Address) - for-range 遍历家庭→房间→设备层级结构 --- ### 02_device_list — 设备列表与过滤 **覆盖 API**: - `client.GetDevices(ctx, opts...)` → `[]*DeviceInfo` - `client.GetDevice(ctx, did)` → `*DeviceInfo` - `client.RefreshDevices(ctx)` → error - `FilterByHome` / `FilterByRoom` / `FilterByOnline` / `FilterByModel` / `FilterByKind` - `DeviceInfo.DeviceKind()` 分类 **演示重点**: - 多种过滤组合(在线+客厅、按型号、按种类) - DeviceKind() 输出 - RefreshDevices 刷新时机 --- ### 03_switch_control — 开关控制 **覆盖 API**: - `devices.Create(client, info)` 工厂 → `Switch` - `Switch.{TurnOn, TurnOff, Toggle, IsOn}(ctx)` - `Switch.OnPropsChanged(handler)` 状态订阅 **演示重点**: - 工厂创建单设备 - TurnOn/TurnOff/Toggle 完整链路 - IsOn 状态查询 - OnPropsChanged 回调演示 --- ### 04_light_control — 灯光控制 **覆盖 API**: - `Light.{TurnOn, TurnOff, Toggle}(ctx)` - `Light.{SetBrightness, GetBrightness}(ctx, pct)` - `Light.{SetColorTemp, GetColorTemp}(ctx, kelvin)` - `Light.{SetColor, GetColor}(ctx, r, g, b)` - `Light.OnPropsChanged(handler)` **演示重点**: - 亮度 0-100 调节 - 色温 2700K-6500K 调节 - RGB 颜色控制 - 不支持功能的降级处理(`GetBrightness` 返回 -1 → 跳过) --- ### 05_ac_control — 空调控制 **覆盖 API**: - `AirConditioner.{TurnOn, TurnOff, IsOn}(ctx)` - `SetMode(ctx, ACMode)` / `GetMode(ctx)` — cool/heat/dry/fan/auto - `SetTargetTemp(ctx, celsius)` / `GetTargetTemp(ctx)` / `GetCurrentTemp(ctx)` - `SetFanSpeed(ctx, FanSpeed)` / `GetFanSpeed(ctx)` — low/medium/high/auto - `SetSwing(ctx, SwingMode)` / `GetSwing(ctx)` — off/vertical/horizontal/both - `SetTargetHumidity(ctx, pct)` / `GetTargetHumidity(ctx)` / `GetCurrentHumidity(ctx)` - `SetAuxHeat(ctx, on)` / `GetAuxHeat(ctx)` - `SetEco(ctx, on)` / `GetEco(ctx)` - `OnPropsChanged(handler)` → `ACState` **演示重点**: - 完整空调控制链路(开→设制冷→设26°C→自动风速→垂直摆风) - OnPropsChanged 实时状态回调 - 不支持的功能优雅降级(如无湿度传感器,跳过湿度设置) --- ### 06_fan_cover — 风扇 + 窗帘控制 **覆盖 API**: - `Fan.{TurnOn, TurnOff, SetSpeed, SetOscillation, SetNaturalWind}(ctx)` - `Cover.{Open, Close, Stop, SetPosition, GetPosition}(ctx)` **演示重点**: - 风扇 4 档调速 + 摇头 + 自然风切换 - 窗帘百分比定位(0%=关, 100%=全开, 50%=半开) - Cover 的 Open/Close/Stop 语义对比 SetPosition --- ### 07_prop_subscribe — 属性/事件/状态订阅 **覆盖 API**: - `client.SubProp(did, siid, piid, PropHandler)` → subID - `client.UnsubProp(did, subID)` - `client.SubEvent(did, siid, eiid, EventHandler)` → subID - `client.UnsubEvent(did, subID)` - `client.SubDeviceState(did, DeviceStateHandler)` - `client.UnsubDeviceState(did)` **演示重点**: - 订阅前后属性值对比 - 等待N秒展示属性/事件推送 - 取消订阅后不再收到回调 - 设备上下线状态监听 --- ### 08_adv_filter_classify — 高级过滤 + 分类 + 工厂模式 **覆盖 API**: - `devices.Classify(info)` → `Kind` 枚举 - `FilterByKind(kind)` 过滤器 - `devices.Create(client, info)` 工厂 → 各设备接口 - `devices.Kind` 所有枚举值 **演示重点**: - 获取全部设备 → 按 Kind 分类 → 统计各类型数量 - 工厂批量创建:遍历 DeviceInfo → Create → type switch 分流 - 不支持的设备返回 nil → continue 跳过 - 输出表格:"设备名 | 型号 | 种类 | 状态" --- ### 09_spec_parser — SPEC 解析器独立使用 **覆盖 API**: - specs 包全部公开 API(如果 specs 是公开的) - SPEC 属性/事件/动作的枚举和查询 **演示重点**: - 无需设备在线即可解析 SPEC - 打印设备有哪些属性(text/switch/select/number/sensor) - 打印设备有哪些事件和动作 --- ## 四、共享配置模块 `config/config.go` ```go package config type Config struct { ClientID string ClientSecret string AccessToken string // OAuth token(从环境变量或文件读取) } // LoadFromEnv 从环境变量加载配置 func LoadFromEnv() (*Config, error) // LoadFromFile 从 JSON 文件加载配置 func LoadFromFile(path string) (*Config, error) ``` **设计原则**: - 所有示例复用一个 config 加载逻辑,避免重复 - 仅 3 个字段,对应 xiaomi.Config - 敏感信息从环境变量或文件读取,不硬编码 --- ## 五、编码规范 ### 5.1 统一约定 ``` 1. 每个示例的 main() 必须有 context.WithTimeout(30s) 2. 所有 IO 操作带 ctx 3. 错误必须处理(不忽略 err) 4. defer cancel() 放在 func main() 顶部 5. 日志用 log 包,不用 fmt.Print(方便区分日志级别) 6. 每个示例一句话说明功能(注释在 main 函数上方) ``` ### 5.2 模板骨架 ```go // Package main demonstrates <功能简述>. // 运行前提:已配置环境变量 XIAOMI_CLIENT_ID / XIAOMI_CLIENT_SECRET / XIAOMI_ACCESS_TOKEN。 package main import ( "context" "log" "time" "xiaomihome/xiaomi" "xiaomihome/xiaomi/devices" "xiaomihome/xiaomi/examples/config" ) func main() { ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) defer cancel() // 1. 加载配置 cfg, err := config.LoadFromEnv() if err != nil { log.Fatal("配置加载失败:", err) } // 2. 创建客户端(零 miot 引用) client, err := xiaomi.NewClient(ctx, xiaomi.Config{ ClientID: cfg.ClientID, ClientSecret: cfg.ClientSecret, AccessToken: cfg.AccessToken, }) if err != nil { log.Fatal("创建客户端失败:", err) } defer client.Close() // 3. 业务逻辑(根据示例不同) // ... } ``` --- ## 六、与 ARCH_PLAN.md 的对应关系 | ARCH_PLAN.md 目标 | 对应示例 | |-------------------|---------| | 用户/家庭/房间信息(GetUserInfo / GetHomeList) | 01_user_home | | 设备列表 + Filter | 02_device_list | | Switch 控制 + OnPropsChanged | 03_switch_control | | Light 控制 | 04_light_control | | AirConditioner 完整控制 | 05_ac_control | | Fan / Cover 控制 | 06_fan_cover | | SubProp / SubEvent / SubDeviceState 订阅 | 07_prop_subscribe | | Classify / FilterByKind / Create 工厂 | 08_adv_filter_classify | | SPEC 解析器 | 09_spec_parser | | context.Context + 错误处理 | 全部示例 | --- ## 七、实施计划 | 序号 | 示例 | 文件 | 优先级 | 复杂度 | |------|------|------|--------|--------| | 0 | config 共享模块 | `config/config.go` | P0 | 小 | | 1 | 用户/家庭/房间 | `01_user_home/main.go` | P0 | 小 | | 2 | 设备列表+过滤 | `02_device_list/main.go` | P0 | 中 | | 3 | 开关控制 | `03_switch_control/main.go` | P0 | 小 | | 4 | 灯光控制 | `04_light_control/main.go` | P0 | 中 | | 5 | 空调控制 | `05_ac_control/main.go` | P0 | 大 | | 6 | 风扇+窗帘 | `06_fan_cover/main.go` | P1 | 中 | | 7 | 订阅通知 | `07_prop_subscribe/main.go` | P1 | 大 | | 8 | 高级过滤+工厂 | `08_adv_filter_classify/main.go` | P1 | 中 | | 9 | SPEC 解析 | `09_spec_parser/main.go` | P2 | 小 | | — | 统一 README | `examples/README.md` | P2 | 小 | --- ## 八、与现有 main.go 的关系 现有 `xiaomi/examples/main.go` 将被**替换**为上述 9 个独立示例。如果作为归档保留,可移到 `examples/_archive/main_old.go`。 --- *本文档已全部实施完成。*