ESP 8266端的程序分为两个部分:simple.py , main.py,其中simple.py直接用uPyLoader传到ESP 8266内,main.py使用umqtt库文件夹中的example_sub.py文件改造,再加上自定义的ESP 8266控制程序。
1、example_sub.py原始文件:
import time
from umqtt.simple import MQTTClient
# Publish test messages e.g. with:
# mosquitto_pub -t foo_topic -m hello
# Received messages from subscriptions will be delivered to this callback
def sub_cb(topic, msg):
print((topic, msg))
def main(server="localhost"):
c = MQTTClient("umqtt_client", server) # MQTT客户端实例
c.set_callback(sub_cb) # 当收到消息时的回调函数, 即收到消息后,对数据进行处理或触发其它动作的函数,自定义编写功能
c.connect() # 接入服务器
c.subscribe(b"foo_topic") # 订阅主题topic, 需自定义修改
while True: # 进入主循环,检查是否有消息到达
if True:
# Blocking wait for message
c.wait_msg()
else:
# Non-blocking wait for message
c.check_msg()
# Then need to sleep to avoid 100% CPU usage (in a real
# app other useful actions would be performed instead)
time.sleep(1)
c.disconnect()
if __name__ == "__main__":
main()
2、micropython中,上电后,首先执行boot.py,然后执行main.py,所以用户功能写在这个文件内。 这里,我把上一步的example_sub.py中的内容修改后,加入main.py,作为连接MQTT服务器的功能函数。程序如下:
from simpleimport MQTTClient # simple.py已经复制到ESP 8266了,所以直接从simple导入MQTTClient
from machineimport Pin # esp 8266的python硬件库
import network # 用于连接WIFI
# 在MQTT的消息回调函数内,主要实现将ESP 8266开发板上的蓝色LED(连接到pin2)指示灯点亮和熄灭的测试,如有需要可以自行添加其它功能。
led= Pin(2, Pin.OUT, value=1)
# Default MQTT server to connect to
SERVER= "0PM6216BMJ.iotcloud.tencentdevices.com" # 根据官方文件(开发者手册一栏)的说明,设置服务器地址
PORT= 1883 # 服务器端口
# 产品名、设备名、密码,作为IotHmac的入口参数
pid= "0BC7N862MJ"
dname= "esp8266"
pwd= b"pa123"
# 在控制台的设备信息一栏中
USERNAME= "0BC7M86BMJesp8266;12010126;DKWDD;1603349745"
PASSWORD= "880c6a8cac1e9326bc2353365324ee24123506bd5ea2450ab387d6acf24df0a83a;hmacsha256" # password: pa123
CLIENT_ID= "0BC7M86BMJesp8266"
TOPIC= b"0BC7M86BMJ/esp8266/info" # 这儿必须加b'', 订阅的主题和控制台->“设备”->“权限列表”中的主题相关
state=
# 消息回调函数
def sub_cb(topic, msg):
global state
if msg== b"on":
# 开led
led.value(0)
state= 1
elif msg== b"off":
# 关led
led.value(1)
state= 0
elif msg== b"toggle":
# 翻转led状态, 0->1,或1->0
led.value(state)
state= 1 - state
# 建立MQTT连接
def main(server=SERVER):
c= MQTTClient(CLIENT_ID, server, PORT, USERNAME, PASSWORD, keepalive=600) # keepalive,设置保持连接的时间,单位秒,这儿设置600秒,如果在这段时间内ESP 8266未向服务器端发送至少一个消息,服务器将断开与它的连接。
# 消息回调函数,对接收到的消息进行自定义的处理
c.set_callback(sub_cb)
c.connect()
c.subscribe(TOPIC)
print("Connected to %s, subscribed to %s topic" % (server, TOPIC))
try:
while 1:
# micropython.mem_info()
c.wait_msg()
finally:
c.disconnect()
# 使ESP 8266连接到WIFI
def wifi_connect():
wlan= network.WLAN(network.STA_IF)
wlan.active(True)
wlan.disconnect()
if not wlan.isconnected():
pass
wlan.connect('TP-LINK_1', '12345678') # wifi 账号和密码
while not wlan.isconnected():
pass
print("wifi is connected")
if __name__== '__main__':
wifi_connect()
main()
3、将上述main.py文件传送到ESP 8266中,就可以建立和服务器的连接了,在控制台的设备列表中可以看到,esp8266处于“在线”状态。
4、连接到服务器后,可以进入设备列表的“操作”下方的“管理”->“在线调试界面”,从服务器发送消息到ESP 8266,进行单向调试,测试程序功能。在调试前,需要弄清楚腾讯云MQTT服务器对topic主题的管理和命名方式:
(1)topic命名方式:产品ID+设备名+自定义名称。
(2)由于topic名和设备名相关联,因此不同设备(如ESP 8266和手机端APP)之间不能直接通过控制台设定的topic进行消息传递。
(3)在“设备”->“权限列表”中罗列了自定义的topic和系统topic的权限,该设备只能使用其中的topic进行上传或订阅消息,“自定义topic”可以增加和删除,在上一层的“产品”管理界面操作。
(4)在“设备”->“在线调试”界面也可以看到,当点击topic选择下拉框时,只能选择和本设备相关的topic。
(5)不同设备之间,要进行消息传递、订阅,需通过设置控制台主界面中的“规则引擎”来进行topic关联。
(6)“规则引擎”里有多种转发方式,这里选择“转发到另一个topic”,就可实现手机端APP发送消息到ESP 8266硬件平台。
5、首先在“产品”->“管理”->“权限列表”中编辑topic的权限(订阅/发布),编辑完成后,在各“设备”的“权限列表”中就会对应的产生变化,这儿可以自己新增一个topic用来测试,取名为info,权限为“发布和订阅”。
6、回到“规则引擎”里,新建一个规则,然后编辑“筛选数据”,设置对接收到的消息进行筛选,“字段”对应的是JSON数据格式的KEY值,下面的“条件”、“当前SQL”也是对应的规则语句,如果前面创建设备时,选择的“自定义数据格式”,那么,这里就可以用通配符“*”,表示不筛选,接收所有消息,“条件”一栏就空着不填; “Topic”设置为消息发布设备的topic,这里设置成手机APP客户端设备的topic(同样为发布和订阅双重权限)。
7、最后“添加行为操作”,“行为类型”选择“数据转发到另一个Topic(Republish)”,“产品”选择另一个设备对应的产品名,“设备”和“Topic”选择esp8266和对应的可订阅的info主题;保存好后,回到“规则引擎”主界面,将“状态”设置为“已激活”。这样,在手机端APP发送的消息就可以通过服务器转发给ESP 8266了。