本例实现通过百度云函数计算,动态创建天工物接入的设备影子,并返回连接信息(影子的用户名&密码);并可搭配规则引擎,实现通过MQTT消息创建影子。
场景1、天工物接入的设备型,给每个设备影子分配了设备唯一的鉴权信息(MQTT用户名+密码),但设备产线可能不具备针对每个设备烧录独一无二信息的能力。
场景2、设备产线具备每个设备逐一收录的能力,但是需动态获取设备对应影子的连接信息。
对场景1,部分情况下可采用物接入(设备型)所提供的组权限(单组鉴权信息最多对应100设备)或者超级权限(可管理所有影子);但是此方案中鉴权信息一旦泄露,设备的消息就有可能被第三方采集或伪造。所以对设备实际使用环境要求较高,一般仅在设备完全处于安全可控情况下、且对设备信息不做安全要求的情况下。
还有一种思路,设备烧录统一的用于初始化的连接信息(MQTT或HTTP均可),对应所连接的服务调用 API 创建设备影子并返回鉴权信息。设备首次联网时建立连接,上报设备唯一标识作为影子名,并获取设备唯一的鉴权信息,随后断开初始化连接,使用本设备唯一的连接信息连接设备影子,开始正常工作。虽然理论上仍存在鉴权信息泄露的风险,但是泄露后最大风险为伪装建立了一些影子,相对前述风险小了很多。而且还可以针对性的通过校验白名单、加密设备标识(设备有双标识情况下还可以交叉验证)等方式进一步减小风险。
对场景2,设备产线同样,可以在产线系统中实时调用 API 创建影子,并获取影子对应的连接信息以烧入设备。
根据以上分析,所以我们需要搭建一个服务(Init Service)用于设备初始化(创建影子、返回鉴权信息)
搭建这个服务可以在自己的主机上,也可以使用一些更轻量级的方案,比如比较火爆的 Serveless 方案。百度云提供了 CFC(函数计算),就可以承担这一任务。
此外,若设备性能较弱,希望裁剪协议支持(如仅支持必须的 MQTT),也可以搭配 IoT Hub + 规则引擎,以 MQTT+CFC 的方式实现。
首先在控制台开通函数计算,创建一个函数。我这里取名叫 creatDevice
。
可根据自己的群控选择语言,我一般 Python,所提供的示例 Demo 也是 Python 的。如需运行示例,可上传 zip 包,将 creatDevice.zip
上传上去。
随后配置一下环境变量,如图添加AK
和SK
,对应填写自己的 AK/SK。获取AK/SK
配置一个物接入数据型实例(或设备型中创建一个Init影子),创建身份拿到 Init 鉴权信息,我的示例中是给了creatdevice
主题发布权限,以及creatdevice/resp
主题的订阅权限。
创建一个规则引擎,在实例和主题
中选择对应实例,输入主题creatdevice
;
在数据目的地
中添加一个 函数计算CFC 的目的地,选择刚才创建的函数,并配置「结果转入主题」为creatdevice/resp
这样就完成了配置。
使用 MQTT 客户端,通过 Init 鉴权信息连接 IoT Hub,订阅(Sub)用于接受返回信息的主题 creatdevice/resp
向主题 creatdevice
发布(Pub)一条消息,内容为
{
"deviceName": "MAC10A4B9000000",
"description": "device shadow created by re & cfc",
"schemaId": "8093f59e-7df2-4207-a28d-cdfd65999ac4"
}
- 其中 schemaId 可以通过 API ,也可以在控制台点开物模型详情页,从 URL 中获取。
然后就可以在主题 creatdevice/resp
中收到鉴权信息。
在大多数情况下,设备的描述信息和物模型都是固定的,所以这部分也可以写入环境变量。
如我添加了 defaultSchemaId
和 defaultDescription
的环境变量,就不需要在请求中带上schemaId
及description
了。
1、鉴权信息(密码)重置:本示例中,同一影子名若重复发送,则会提示影子已经存在
2、白名单或其他加密或验证方式