事件与订阅
该 SDK 提供了一套事件驱动架构,支持订阅节点与设备的实时状态更新。具体包括本地网络发现事件和节点更新通知。
概览
事件订阅系统支持以下功能:
- 实时本地发现:自动检测节点何时在本地网络上变为可用。
- 传输管理:动态更新节点传输配置。
- 节点更新:接收节点状态变更通知。
- 灵活回调:为不同事件类型注册自定义处理器。
事件类型
通过 ESPRMEventType 枚举,SDK 支持以下事件类型:
| 事件类型 | 描述 |
|---|---|
localDiscovery | 在本地网络发现节点时触发,用于更新节点传输配置。 |
nodeUpdates | 节点状态变更(参数更新、连接变化等)时触发。 |
本地发现与传输更新
工作原理
本地发现机制遵循以下流程:
步骤 1:注册本地发现回调
若要接收本地发现事件,可使用 subscribe 方法注册回调:
import { ESPRMEventType } from "@espressif/rainmaker-base-sdk";
// 定义用于处理已发现节点的回调
const localDiscoveryCallback = (discoveredNodeData) => {
console.log("Node discovered locally:", discoveredNodeData);
// discoveredNodeData 包含:
// - nodeId:已发现节点的 ID
// - transportDetails:包含 baseUrl 的传输配置
const { nodeId, transportDetails } = discoveredNodeData;
// 将新的传输信息写入节点存储
// 这样可通过本地网络与节点通信
updateNodeTransport(nodeId, transportDetails);
};
// 订阅本地发现事件
try {
userInstance.subscribe(ESPRMEventType.localDiscovery, localDiscoveryCallback);
console.log("Subscribed to local discovery events");
} catch (error) {
console.error("Error subscribing to local discovery:", error);
}
重要信息:节点存储访问
回调应能访问节点存储(或等效的状态管理系统),这样当在本地发现节点时,可以用本地传输详情更新该节点的 availableTransports 字段。availableTransports 的类型是 Record<ESPTransportMode, ESPTransportConfig>,每个传输模式映射到其配置。
步骤 2:SDK 启动发现
当以 ESPRMEventType.localDiscovery 调用 subscribe 方法时:
- SDK 注册回调:回调会存入内部的
eventCallbacks注册表。 - 创建发现管理器:以本地协议创建
ESPDiscoveryManager实例。 - 开始发现:管理器调用
startDiscovery(),使用ESPDiscoveryAdapter扫描本地网络。 - 触发回调:发现节点后,以节点详情调用回调。
// 订阅本地发现事件时上述操作会在 SDK 内部自动发生
// 无需手动调用这些方法,只需订阅即可
// SDK 内部流程(供参考):
// 1. eventCallbacks[ESPRMEventType.localDiscovery].push(callback)
// 2. new ESPDiscoveryManager(ESPDiscoveryProtocol.local)
// 3. localDiscoveryManager.startDiscovery(discoveryCallback)
需要发现适配器
要启用本地发现功能,必须在 SDK 初始化期间配置 ESPDiscoveryAdapter。更多信息请查看适配器文档。
步骤 3:更新节点传输
当回调接收到发现事件时,更新节点的可用传输:
// 示例:在状态管理中更新节点传输
const localDiscoveryCallback = (discoveredNodeData) => {
const { nodeId, transportDetails } = discoveredNodeData;
// transportDetails 结构:
// {
// type: "local",
// metadata: {
// baseUrl: "http://192.168.1.100" // 节点的本地 IP
// }
// }
// 在存储中查找该节点
const node = findNodeById(nodeId);
if (node) {
// 若不存在则将 availableTransports 初始化为 Record
node.availableTransports = node.availableTransports || {};
// 添加或更新本地传输配置
// availableTransports 的类型是 Record<ESPTransportMode, ESPTransportConfig>
node.availableTransports[transportDetails.type] = transportDetails;
console.log(
`Node ${nodeId} is now available locally at ${transportDetails.metadata.baseUrl}`
);
}
};
传输优先级
设置传输顺序
setTransportOrder 方法用于定义 SDK 与节点通信(例如设置设备参数)时应使用的传输优先级。
import { ESPRMBase, ESPTransportMode } from "@espressif/rainmaker-base-sdk";
// 定义传输优先级:先尝试本地,回退到云端
const transportOrder = [
ESPTransportMode.local, // 最高优先级
ESPTransportMode.cloud, // 回退
];
try {
ESPRMBase.setTransportOrder(transportOrder);
console.log("Transport order set successfully");
} catch (error) {
console.error("Error setting transport order:", error);
}
传输优先级策略
- 本地优先:设置
[ESPTransportMode.local, ESPTransportMode.cloud],在同一网络时可获得更快的响应。 - 云端优先:设置
[ESPTransportMode.cloud, ESPTransportMode.local],无论网络位置如何行为更一致。