ESP32通过MQTT协议把数据上传到OntNet平台(网络层)
文章目录
前言
由于之前的代码变量定义的比较乱,很多地方不容易理解,而且长时间没有使用过,所以重新调试了一个比较简洁的程序,也算重新温习一下,其中上传的数据由传感器数据修改为自定义的一个数据,如果需要上传其他传感器数据,直接修改上传的数据就可以。
可搭配前两篇介绍一起学习呀!!!
Thonny+MicroPython+ESP32开发环境搭建
一、认识OneNet云平台
1.One Net注册新用户
首先,进入中国移动OneNet平台官方网站 https://open.iot.10086.cn ,点击右上角的“注册”,注册一个账号。账号注册完成后点击登录,进入右上角的“控制台”,如图下图所示。
2.添加新产品
点击添加产品,填入产品参数,如图所示。
以上参数可以根据需要设置,查看产品的参数,里面的产品ID很重要,后面的身份认证需要用到。
3.添加新设备
进入创建的产品,点击添加设备。这里创建一个测试设备,如下图所示
云平台的使用就这么多,还有其他很多功能这里不一一介绍,可以到官网进行学习。
二、数据上传
1.导入库及连接WIFI
from simple import MQTTClient
from machine import Pin,Timer
import network,time
其中network库是连接WIFI的库,simple库是MQTT协议程序,这个我放在下面链接可以自行下载使用,包含simple.py和完整代码。
链接:https://pan.baidu.com/s/1Q6lAEy7b7Hd_Kcue43spOg?pwd=8888
提取码:8888
def WIFI_Connect():
wlan = network.WLAN(network.STA_IF)
wlan.active(True)
start_time = time.time()
if not wlan.isconnected():
print("connecting to network...")
wlan.connect('aaaaa', '11111111')
while not wlan.isconnected():
WIFI_LED.value(1)
time.sleep_ms(300)
WIFI_LED.value(0)
time.sleep_ms(300)
if time.time()-start_time > 15:
print("WIFI Connected Timeout!")
break
if wlan.isconnected():
WIFI_LED.value(1)
return True
else:
return False
上面是连接WIFI的函数,只有连接了网络才能把数据上传到云平台,上面定义的WIFI_LED是LED可查看完整代码。
2.数据上传函数及回调上传函数
使用数据上传函数将数据上传到云平台,这里是使用一个定时器实时将数据上传到云平台,其中a变量是自定义的数据用来模拟传感器的数据。
def MQTT_Send(tim):
global a
a+=1
if(a>=999):
a=0
mymessage = ('{
"id": 123,"dp": {
"data": [{
"v": %d}]}}')%a #上传的数据需要按照这个格式
client.publish(topic=publish_TOPIC,msg=mymessage,retain=False,qos=0)
client.check_msg()#检查有没有发信息
回调函数还没有仔细调试,估计没什么问题,主要用于数据下发,由于会在应用层中用到,这里提前粘贴出来。
#设置MQTT回调函数,有信息时候执行
def MQTT_callback(topic,msg):
print('topic:{}'.format(topic))
print('msg:{}'.format(msg))
s=str(topic,'utf-8').split('/')
print(s[5])
response_TOPIC='$sys/417488/test/cmd/response/'+s[5]
res_msg='success'
client.publish(topic=response_TOPIC,msg=res_msg,retain=False,qos=0)
#print((topic,msg))
if msg == b"1":
WIFI_LED.value(1)
print("1")
elif msg == b"0":
WIFI_LED.value(0)
print("0")
三、身份认证
设备接入OneNet平台需要一个身份认证,相当于账号密码,用户名是产品ID,用户密码是用token工具计算的。token工具下载网站:https://open.iot.10086.cn/doc/mqtt/book/manual/auth/tool.html
打开 token生成工具 token.exe,填写对应参数,点击generate,生成token,如图所示
红框是我们需要的密码,其中
res参数格式如:products/{产品ID}/devices/{设备名称}其中产品ID上面有提到。
et参数是一个时间参数这里取一个远大于当前时间的就可以如:1700000000
key参数是设备的key这里打开设备列表再点击详情就可以找到,如下图:
其他参数和我上面设置成一样就可以,最后点击Generate就生成完成。这里的每一步都不能出错,否则设备和云平台是连接不上的。
四、完整代码
from simple import MQTTClient
from machine import Pin,Timer
import network,time
WIFI_LED = Pin(2,Pin.OUT)
#自定义用于模拟传感器数据
a=0
#连接WIFI的函数
def WIFI_Connect():
wlan = network.WLAN(network.STA_IF)
wlan.active(True)
start_time = time.time()
if not wlan.isconnected():
print("connecting to network...")
wlan.connect('aaaaa', '11111111')
while not wlan.isconnected():
WIFI_LED.value(1)
time.sleep_ms(300)
WIFI_LED.value(0)
time.sleep_ms(300)
if time.time()-start_time > 15:
print("WIFI Connected Timeout!")
break
if wlan.isconnected():
WIFI_LED.value(1)
return True
else:
return False
#数据上传函数
def MQTT_Send(tim):
global a
a+=1
if(a>=999):
a=0
mymessage = ('{"id": 123,"dp": {"data": [{ "v": %d}]}}')%a
client.publish(topic=publish_TOPIC,msg=mymessage,retain=False,qos=0)
client.check_msg()#检查有没有发信息
#设置MQTT回调函数,有信息时候执行
def MQTT_callback(topic,msg):
print('topic:{}'.format(topic))
print('msg:{}'.format(msg))
s=str(topic,'utf-8').split('/')
print(s[5])
response_TOPIC='$sys/417488/test/cmd/response/'+s[5]
res_msg='success'
client.publish(topic=response_TOPIC,msg=res_msg,retain=False,qos=0)
#print((topic,msg))
if msg == b"1":
WIFI_LED.value(1)
print("1")
elif msg == b"0":
WIFI_LED.value(0)
print("0")
if __name__ == "__main__":
WIFI_Connect()
if WIFI_Connect():
#TOPIC名称 格式:$sys/{产品ID}/{设备名称}/dp/post/json
publish_TOPIC = "$sys/417488/test/dp/post/json"
#这个参数和上面那个差不多,只需要修改两个地方
subscribe_TOPIC = "$sys/417488/test/cmd/request/+"
#客户端ID:设备名称
CLIENT_ID = "test"
#用户名:产品ID
user_name = "417488"
#用户密码:用token工具计算
user_password = "version=2018-10-31&res=products%2F417488%2Fdevices%2Ftest&et=1700000000&method=md5&sign=8II9kM5pBQJ%2FZ%2B8Wl8RItA%3D%3D"
SERVER = "183.230.40.96"
PORT = 1883
client = MQTTClient(CLIENT_ID, SERVER, 0, user_name, user_password, 60)
#设置回调函数
client.set_callback(MQTT_callback)
client.connect()
#订阅主题
client.subscribe(subscribe_TOPIC)
tim = Timer(-1)
tim.init(period=1000, mode=Timer.PERIODIC,callback=MQTT_Send)#周期为 1000ms
五、总结
这是基本的数据上传程序,如果需要上传更多数据,修改一下就可以,之后会有应用层关于app命令下发的相关介绍。