ESP 8266端的程序分為兩個部分:simple.py , main.py,其中simple.py直接用uPyLoader傳到ESP 8266內(nèi)涮因,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)?????????????????????????????????????????????? # 當收到消息時的回調(diào)函數(shù), 即收到消息后动知,對數(shù)據(jù)進行處理或觸發(fā)其它動作的函數(shù),自定義編寫功能
? ? c.connect()?????????????????????????????????????????????????????????????? # 接入服務器
? ? c.subscribe(b"foo_topic")??????????????????????????????????????? # 訂閱主題topic员辩, 需自定義修改
? ? while True:????????????????????????????????????????????????????????????? # 進入主循環(huán)盒粮,檢查是否有消息到達
? ? ? ? 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中奠滑,上電后丹皱,首先執(zhí)行boot.py妒穴,然后執(zhí)行main.py,所以用戶功能寫在這個文件內(nèi)摊崭。? 這里讼油,我把上一步的example_sub.py中的內(nèi)容修改后,加入main.py呢簸,作為連接MQTT服務器的功能函數(shù)汁讼。程序如下:
???? from simpleimport MQTTClient?????????????????????????????????????? # simple.py已經(jīng)復制到ESP 8266了,所以直接從simple導入MQTTClient
???? from machineimport Pin???????????????????????????????????????????????? # esp 8266的python硬件庫
???? import network??????????????????????????????????????????????????? ? ??????? # 用于連接WIFI
# 在MQTT的消息回調(diào)函數(shù)內(nèi)阔墩,主要實現(xiàn)將ESP 8266開發(fā)板上的藍色LED(連接到pin2)指示燈點亮和熄滅的測試,如有需要可以自行添加其它功能瓶珊。
led= Pin(2, Pin.OUT, value=1)
# Default MQTT server to connect to
SERVER= "0PM6216BMJ.iotcloud.tencentdevices.com"??????????????????????????? # 根據(jù)官方文件(開發(fā)者手冊一欄)的說明啸箫,設置服務器地址
PORT= 1883?????????????????????????????????????????????????????????????????????????????????????????????? # 服務器端口
# 產(chǎn)品名、設備名伞芹、密碼忘苛,作為IotHmac的入口參數(shù)
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'', 訂閱的主題和控制臺->“設備”->“權(quán)限列表”中的主題相關(guān)
state=
# 消息回調(diào)函數(shù)
def sub_cb(topic, msg):
????????????? global state
???????????? if msg== b"on":
? ?????????? # 開led
? ? ? ? ? ? ? led.value(0)
? ??????????? state= 1
????????????? elif msg== b"off":
? ?????????? # 關(guān)led
? ? ? ? ? ? ? led.value(1)
? ???????????? state= 0
???????????? elif msg== b"toggle":
? ? ? ? ? ? ?? # 翻轉(zhuǎn)led狀態(tài)唱较, 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秒,如果在這段時間內(nèi)ESP 8266未向服務器端發(fā)送至少一個消息汉形,服務器將斷開與它的連接纸镊。
? ??????????????? # 消息回調(diào)函數(shù),對接收到的消息進行自定義的處理
? ? ? ? ? ? ? ? ?? 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處于“在線”狀態(tài)凯旭。
4、連接到服務器后使套,可以進入設備列表的“操作”下方的“管理”->“在線調(diào)試界面”罐呼,從服務器發(fā)送消息到ESP 8266,進行單向調(diào)試童漩,測試程序功能弄贿。在調(diào)試前,需要弄清楚騰訊云MQTT服務器對topic主題的管理和命名方式:
(1)topic命名方式:產(chǎn)品ID+設備名+自定義名稱矫膨。
(2)由于topic名和設備名相關(guān)聯(lián)差凹,因此不同設備(如ESP 8266和手機端APP)之間不能直接通過控制臺設定的topic進行消息傳遞期奔。
(3)在“設備”->“權(quán)限列表”中羅列了自定義的topic和系統(tǒng)topic的權(quán)限,該設備只能使用其中的topic進行上傳或訂閱消息危尿,“自定義topic”可以增加和刪除呐萌,在上一層的“產(chǎn)品”管理界面操作。
(4)在“設備”->“在線調(diào)試”界面也可以看到谊娇,當點擊topic選擇下拉框時肺孤,只能選擇和本設備相關(guān)的topic。
(5)不同設備之間济欢,要進行消息傳遞赠堵、訂閱,需通過設置控制臺主界面中的“規(guī)則引擎”來進行topic關(guān)聯(lián)法褥。
(6)“規(guī)則引擎”里有多種轉(zhuǎn)發(fā)方式茫叭,這里選擇“轉(zhuǎn)發(fā)到另一個topic”,就可實現(xiàn)手機端APP發(fā)送消息到ESP 8266硬件平臺半等。
5揍愁、首先在“產(chǎn)品”->“管理”->“權(quán)限列表”中編輯topic的權(quán)限(訂閱/發(fā)布),編輯完成后杀饵,在各“設備”的“權(quán)限列表”中就會對應的產(chǎn)生變化莽囤,這兒可以自己新增一個topic用來測試,取名為info切距,權(quán)限為“發(fā)布和訂閱”朽缎。
6、回到“規(guī)則引擎”里蔚舀,新建一個規(guī)則饵沧,然后編輯“篩選數(shù)據(jù)”,設置對接收到的消息進行篩選赌躺,“字段”對應的是JSON數(shù)據(jù)格式的KEY值狼牺,下面的“條件”、“當前SQL”也是對應的規(guī)則語句礼患,如果前面創(chuàng)建設備時是钥,選擇的“自定義數(shù)據(jù)格式”,那么缅叠,這里就可以用通配符“*”悄泥,表示不篩選,接收所有消息肤粱,“條件”一欄就空著不填弹囚; “Topic”設置為消息發(fā)布設備的topic,這里設置成手機APP客戶端設備的topic(同樣為發(fā)布和訂閱雙重權(quán)限)领曼。
7鸥鹉、最后“添加行為操作”蛮穿,“行為類型”選擇“數(shù)據(jù)轉(zhuǎn)發(fā)到另一個Topic(Republish)”,“產(chǎn)品”選擇另一個設備對應的產(chǎn)品名毁渗,“設備”和“Topic”選擇esp8266和對應的可訂閱的info主題践磅;保存好后,回到“規(guī)則引擎”主界面灸异,將“狀態(tài)”設置為“已激活”府适。這樣,在手機端APP發(fā)送的消息就可以通過服務器轉(zhuǎn)發(fā)給ESP 8266了肺樟。