文章內(nèi)容較長,下面把目錄給大家,需要的小伙伴可以只看自己需要觀看對應部分!
一、前言
二、設計思路
三、華為云IOT平臺
3.1 創(chuàng)建產(chǎn)品
3.2 創(chuàng)建設備
3.3 模擬設備上云測試
四、設備數(shù)據(jù)轉(zhuǎn)存
4.1 創(chuàng)建OSB存儲桶
4.2 配置數(shù)據(jù)轉(zhuǎn)發(fā)規(guī)則
五、應用側(cè)-可視化大屏開發(fā)
5.1 應用側(cè)接口
5.2 查詢設備影子數(shù)據(jù)接口
5.3 接口調(diào)試
5.5 接口總結(jié)
5.5 如何獲取X-Subject-Token
5.6 查詢設備影子數(shù)據(jù)代碼
5.7 界面設計最終效果
六、硬件部分
6.1 MQTT版本
6.2 BC26上云配置代碼
當前的場景是,在高速公路上部署溫度采集設備,在高速路地表安裝溫度檢測傳感器,檢測當前路段的路面實際溫度。一段高速路上有多個地點需要采集溫度數(shù)據(jù)。 采集溫度數(shù)據(jù)需要上傳到云平臺進行數(shù)據(jù)存儲,并且通過可視化界面展示溫度變化曲線,支持查詢最近幾天的溫度信息。
(1)云平臺選型:使用華為云物聯(lián)網(wǎng)云平臺。
(2)云數(shù)據(jù)存儲: 使用OBS存儲,存放設備上傳的歷史數(shù)據(jù)。
(3)設備選項:NBIOT模塊+溫度采集模塊,實現(xiàn)溫度采集上報。
(4)數(shù)據(jù)可視化:采用華為云IoT應用側(cè)接口,獲取傳感器設備上傳到云端的數(shù)據(jù),在本地設計界面進行可視化顯示溫度數(shù)據(jù)。
下面是溫度數(shù)據(jù)可視化展示效果:
本篇文章主要介紹設備上云的詳細流程,介紹華為云物聯(lián)網(wǎng)云端產(chǎn)品、設備創(chuàng)建流程,數(shù)據(jù)轉(zhuǎn)存方式,應用側(cè)開發(fā)接口等等。
硬件選型:
(1)STM32開發(fā)板: STM32F103C8T6
(2)NBIOT模塊--BC26
BC26模塊是一款高性能、低功耗、多頻段LTE Cat NB1無線通信模塊。
(3)溫度采集模塊
pt100是鉑熱電阻,它的阻值會隨著溫度的變化而改變。PT后的100即表示它在0℃時阻值為100歐姆,在100℃時它的阻值約為138.5歐姆。其工作原理:當PT100在0℃時,其電阻為100歐姆。它的電阻會隨著溫度的升高而上升,并且它的電阻會勻速增加。
熱電阻是一種常用于中低溫的溫度傳感器。它的工作原理是基于電阻的熱效應,即電阻的阻值隨溫度的變化而變化。鉑金熱敏電阻的熱阻精度最高,具有抗振動、穩(wěn)定性好、耐高壓等特點。因此,它被制成各種標準溫度計進行測量和校準。
官網(wǎng)地址: https://www.huaweicloud.com/
(1)設備接入IOTDA
在產(chǎn)品頁面找到iot物聯(lián)網(wǎng),選擇設備接入IOTDA
設備接入服務(IoT Device Access)是華為云的物聯(lián)網(wǎng)平臺,提供海量設備連接上云、設備和云端雙向消息通信、批量設備管理、遠程控制和監(jiān)控、OTA升級、設備聯(lián)動規(guī)則等能力,并可將設備數(shù)據(jù)靈活流轉(zhuǎn)到華為云其他服務,幫助物聯(lián)網(wǎng)行業(yè)用戶快速完成設備聯(lián)網(wǎng)及行業(yè)應用集成,基礎版每月一百萬條消息免費。
在頁面上選擇免費試用。
點擊后,會進入到設備接入控制臺頁面。
(2)設備接入地址
在基礎版詳情頁面,點擊右邊的按需計費詳情,可以查看物聯(lián)網(wǎng)服務器接入的IP地址,端口號、接入方式。
如果是設備接入,可以選擇MQTT或者MQTTS協(xié)議,在單片機上只有MQTT協(xié)議驗證比較方便,通過MQTT三元組即可完成設備連接,當前我這里的設備選擇是MQTT協(xié)議連接華為云平臺。
域名:a161a58a78.iot-mqtts.cn-north-4.myhuaweicloud.com
(3)創(chuàng)建產(chǎn)品
在左邊選項卡里點擊產(chǎn)品,進入產(chǎn)品頁面,點擊右上角創(chuàng)建產(chǎn)品。
根據(jù)自己的產(chǎn)品信息,填寫表單:
(4)完成產(chǎn)品創(chuàng)建
點擊查看詳情,可以進入到創(chuàng)建成功的產(chǎn)品頁面。
(4)定義產(chǎn)品模型
產(chǎn)品創(chuàng)建之后,接著需要在平臺上構(gòu)建一款設備的抽象模型,使平臺理解該款設備支持的功能。
比如:溫度采集設備肯定會向云平臺上傳采集的溫度信息;在產(chǎn)品模型里就可以定義一個溫度的屬性字段。
選擇下面的自定義模型。
添加服務ID。
添加屬性。
新增屬性字段。
當前在多節(jié)點溫度采集的設備里,主要是采集溫度上傳,這里就新增一個溫度的屬性。
產(chǎn)品模型創(chuàng)建完成。
(1)創(chuàng)建單個設備
設備注冊的方式有很多:
【1】創(chuàng)建支持單個設備手動創(chuàng)建。
【2】如果設備特別多可以選擇批量注冊。
【3】通過API接口進行動態(tài)注冊。
當前為了演示流程,這里選擇第一種方式,手動創(chuàng)建單個設備。
在設備頁面,選擇所有設備選項,點擊右邊的注冊設備按鈕。
(2)單設備注冊填寫信息
點擊注冊設備之后,會彈出一個表單填寫信息。
其中產(chǎn)品就選擇剛才創(chuàng)建的產(chǎn)品,設備標識碼這一項一般是填設備的ID(設備的唯一標識符,方便綁定設備)。目前還沒有對接硬件,我這里就填dev1,方便接下來的測試。
下面的設備ID這一項如果不填,會自動生成,可以不管;最后輸入密匙(這個密匙的作用:通過對每個設備進行身份驗證,可以安全地將每個設備連接到平臺,并且安全地管理這些設備),填好之后點擊確定。
(3)設備創(chuàng)建完成
創(chuàng)建好之后,保存生成的設備ID和密匙。
得到的密匙和ID的格式文本如下:
????"device_id":?"6353a8163ec34a6d03c8dfe5_dev1",
這個設備密匙和ID,后面生成MQTT登錄參數(shù)時需要用到。
(4)創(chuàng)建多個溫度設備節(jié)點
由于本項目是實現(xiàn)多節(jié)點溫度上傳到云平臺,每個節(jié)點都是一個獨立的溫度采集設備,為了方便演示效果,還需要多創(chuàng)建幾個設備。
接下來的創(chuàng)建流程,和剛才第一個設備一樣,這里就不再截圖演示了。
點擊創(chuàng)建設備按鈕,繼續(xù)注冊。
目前一共創(chuàng)建了4個設備,其中main_dev設備是用來作為顯示終端,在本地用顯示屏顯示其他溫度采集節(jié)點采集的溫度信息。 剩下3個設備dev1,dev2,dev3是表示3個獨立的溫度采集節(jié)點。
這4個設備的密匙和ID信息如下:
????"device_id":?"6353a8163ec34a6d03c8dfe5_dev1",
????"device_id":?"6353a8163ec34a6d03c8dfe5_dev2",
????"device_id":?"6353a8163ec34a6d03c8dfe5_dev3",
????"device_id":?"6353a8163ec34a6d03c8dfe5_main_dev",
目前設備創(chuàng)建之后,這些設備都還沒有激活。接下來會使用MQTT客戶端來模擬真實設備上云,上傳溫度數(shù)據(jù)。
這里的上云,包括數(shù)據(jù)交互都采用MQTT客戶端來模擬實現(xiàn),不涉及到實際的硬件,只要模擬能測試成功,并且能得到自己想要的結(jié)果,那硬件就沒有問題了。
(1)生成MQTT鑒權(quán)三元組
設備要連接華為云平臺的方式,在第一節(jié)創(chuàng)建產(chǎn)品的時候就已經(jīng)介紹了,本次項目里的設備是采用MQTT協(xié)議接入云平臺。 在完成設備模擬上云之前,需要先生成設備的MQTT協(xié)議鑒權(quán)三元組。
華為云提供了一個在線工具,用來生成MQTT鑒權(quán)三元組: https://iot-tool.obs-website.cn-north-4.myhuaweicloud.com/
工具打開的界面如下效果:
前面兩行就是填設備創(chuàng)建后生成的設備ID和設備密匙,填好之后,生成下面3行信息,生成的3行就是MQTT協(xié)議登錄需要用的參數(shù)。
按照格式分別生成4個設備的鑒權(quán)信息:
得到的三元組如下:
ClientId??6353a8163ec34a6d03c8dfe5_dev1_0_0_2022102209
Username??6353a8163ec34a6d03c8dfe5_dev1
Password??c58c45d514832b119b4302eafb3e74854849ca94079e9aed75efedf176e9c388
ClientId??6353a8163ec34a6d03c8dfe5_dev2_0_0_2022102209
Username??6353a8163ec34a6d03c8dfe5_dev2
Password??c58c45d514832b119b4302eafb3e74854849ca94079e9aed75efedf176e9c388
ClientId??6353a8163ec34a6d03c8dfe5_dev3_0_0_2022102209
Username??6353a8163ec34a6d03c8dfe5_dev3
Password??c58c45d514832b119b4302eafb3e74854849ca94079e9aed75efedf176e9c388
ClientId??6353a8163ec34a6d03c8dfe5_main_dev_0_0_2022102209
Username??6353a8163ec34a6d03c8dfe5_main_dev
Password??c58c45d514832b119b4302eafb3e74854849ca94079e9aed75efedf176e9c388
(2)MQTT客戶端模擬設備登錄
得到MQTT三元組之后,接下來用MQTT客戶端模擬設備登錄云平臺。
按照軟件的輸入框提示,輸入對應的信息,點擊登錄。 其中的IP地址和端口號在第一小節(jié)的產(chǎn)品創(chuàng)建里就介紹過了。 后面輸入的這3行就是上一步生成的MQTT鑒權(quán)三元組。
登錄成功。
然后打開云平臺的控制臺,查看設備在線情況:
可以看到dev1已經(jīng)在線了, 剛才模擬的設備就是dev1。
(3)主題訂閱與發(fā)布
目前設備已經(jīng)成功登錄,接下來要解決的問題就是數(shù)據(jù)傳輸問題了。
MQTT協(xié)議里要理解的兩個概念就是主題訂閱,主題發(fā)布。 設備上傳數(shù)據(jù)到平臺,屬于 主題發(fā)布。 設備想要知道其他設備的數(shù)據(jù)或者云平臺下發(fā)的指令,需要進行主題訂閱。
幫助文檔的地址: https://support.huaweicloud.com/api-iothub/iot_06_v5_3002.html
MQTT消息由固定報頭(Fixed header)、可變報頭(Variable header)和有效載荷(Payload)三部分組成。
其中固定報頭(Fixed header)和可變報頭(Variable header)格式的填寫請參考MQTT標準規(guī)范,有效載荷(Payload)的格式由應用定義,即設備和物聯(lián)網(wǎng)平臺之間自己定義。
常見MQTT消息類型主要有CONNECT、SUBSCRIBE、PUBLISH。
CONNECT:指客戶端請求和服務端連接。有效載荷(Payload)的主要參數(shù),參考設備連接鑒權(quán)填寫。
SUBSCRIBE:指客戶端訂閱請求。有效載荷(Payload)中的主要參數(shù)“Topic?name”,參考Topic定義中訂閱者為設備的Topic。
可變報頭(Variable?header)中的主要參數(shù)“Topic?name”,指設備上報到物聯(lián)網(wǎng)平臺時發(fā)布者為設備的Topic。詳細請參考Topic定義。
有效載荷(Payload)中的主要參數(shù)為完整的數(shù)據(jù)上報和命令下發(fā)的消息內(nèi)容,目前是一個JSON對象。
上行Topic是指設備向平臺發(fā)送請求,或上報數(shù)據(jù),或回復響應。
下行Topic是指平臺向設備下發(fā)指令,或回復響應。
設備與平臺建立連接后,需要訂閱下行Topic,否則無法收到平臺下發(fā)的指令或回復的響應。應用側(cè)接口的調(diào)用,需要設備側(cè)的配合,例如應用側(cè)下發(fā)命令,設備側(cè)需要先訂閱“平臺命令下發(fā)”的下行Topic,否則設備無法收到平臺命令,應用下發(fā)命令的接口也會報超時。
在產(chǎn)品頁面,可以看到主題的格式,以及對于主題的用途:**
【1】訂閱主題
對于設備而言,一般會訂閱平臺下發(fā)消息給設備 這個主題。
設備想接收平臺下發(fā)的消息,就需要訂閱平臺下發(fā)消息給設備 的主題,訂閱后,平臺下發(fā)消息給設備,設備就會收到消息。
主題的格式如下:
$oc/devices/{device_id}/sys/messages/down
$oc/devices/6353a8163ec34a6d03c8dfe5_dev1/sys/messages/down
【2】發(fā)布主題
對于設備,發(fā)布主題,也就顯示向云平臺上傳數(shù)據(jù)。
發(fā)布的主題格式如下:
$oc/devices/{device_id}/sys/properties/report
$oc/devices/6353a8163ec34a6d03c8dfe5_dev1/sys/properties/report
發(fā)布主題時,需要上傳數(shù)據(jù),這個數(shù)據(jù)格式是JSON格式。
上傳的JSON數(shù)據(jù)格式如下:
??????"service_id":?<填服務ID>,
??????"<填屬性名稱1>":?<填屬性值>,
??????"<填屬性名稱2>":?<填屬性值>,
根據(jù)JSON格式,一次可以上傳多個屬性字段。 這個JSON格式里的,服務ID,屬性字段名稱,屬性值類型,在前面創(chuàng)建產(chǎn)品的時候就已經(jīng)介紹了,不記得可以翻到前面去查看。
根據(jù)這個格式,組合溫度節(jié)點一次上傳的數(shù)據(jù):
{"services":?[{"service_id":?"temp","properties":{"temp":24.6}}]}
(4)MQTT客戶端模擬設備上報數(shù)據(jù)
打開MQTT客戶端填入訂閱主題,發(fā)布主題,和需要發(fā)布的數(shù)據(jù),然后分別點擊訂閱主題按鈕,發(fā)布主題按鈕。 右邊提示成功之后,就可以打開云平臺看上傳的效果了。 (這里是以dev1,設備1為例)
打開云平臺看到dev1已經(jīng)在線。
點擊dev1,進去查看設備上傳的數(shù)據(jù)。 可以看到,剛才上傳的數(shù)據(jù)已經(jīng)收到了。
到此,設備上傳數(shù)據(jù)到云平臺已經(jīng)完成。
如果設備上傳的數(shù)據(jù)需要進行保存,后續(xù)進行分析做其他用途,可以利用數(shù)據(jù)轉(zhuǎn)發(fā)服務,讓平臺將設備上報數(shù)據(jù)推送給自己的應用服務器,由應用服務器進行保存;也可以選擇讓平臺將設備上報數(shù)據(jù)轉(zhuǎn)發(fā)給OBS對象存儲服務,由OBS進行存儲,進行永久保存,非常方便。如果存儲在OBS里,自己設計應用側(cè)界面時,也可以直接拉取OBS里的數(shù)據(jù)下來進行顯示,處理,分析。
對象存儲服務(Object Storage Service,OBS)是一個基于對象的存儲服務,提供了海量、安全、高可靠、低成本的數(shù)據(jù)存儲能力。
(1)選擇管理控制臺
(2)創(chuàng)建桶
填充桶信息: 我這里選擇的是 華北-北京一
我這里因為要長期使用,這里選擇1年的購買權(quán)。
(3)創(chuàng)建成功
(1)創(chuàng)建規(guī)則
選擇左側(cè)導航欄的規(guī)則>數(shù)據(jù)轉(zhuǎn)發(fā),單擊右上角的創(chuàng)建規(guī)則。
填充規(guī)則轉(zhuǎn)發(fā)的信息:
(2)設置轉(zhuǎn)發(fā)目標
單擊添加,設置轉(zhuǎn)發(fā)目標。
這里的區(qū)域選擇--華北-北京一。 因為前面的OBS桶創(chuàng)建的時候,設置區(qū)域設置的是北京一,然后點擊授權(quán)。
授權(quán)之后,選擇剛才創(chuàng)建的OBS桶,設置存儲數(shù)據(jù)的目錄和文件名字。
存儲的數(shù)據(jù)可以直接轉(zhuǎn)存JSON數(shù)據(jù)到OBS存儲桶,也可以存放成CSV文件到存儲桶。
如果選擇存儲JSON,就是直接將設備上傳的數(shù)據(jù)存放到OBS存儲里,如果選擇存儲CSV文件,可以自己選擇需要存儲的字段。 下面我演示一下存儲成CSV文件時如何進行設置。 (選擇JSON文件不需要進行任何設置,直接將設備上傳的數(shù)據(jù)JSON存儲進去了)。
下面設置轉(zhuǎn)發(fā)的字段: (如果提示沒有授權(quán),點擊授權(quán)即可)
這個轉(zhuǎn)發(fā)字段就是表示需要存放的數(shù)據(jù)是那些,對于路燈而言,肯定是需要存儲上報的溫度、濕度、電量、光照強度的屬性的。 這些屬性在創(chuàng)建產(chǎn)品的時候設置,設備上報的也是這些屬性。
這是設備上傳一次云平臺的完整JSON數(shù)據(jù)格式:
??"resource":?"device.property",
??"event_time":?"20221018T131627Z",
??"request_id":?"5ee95a0c-262d-43c3-8d31-af453f9952ef",
??????"app_id":?"7211833377cf435c8c0580de390eedbe",
??????"device_id":?"634e3e423ec34a6d03c84bfb_1126626497",
??????"node_id":?"1126626497",
??????"product_id":?"634e3e423ec34a6d03c84bfb",
??????"gateway_id":?"634e3e423ec34a6d03c84bfb_1126626497"
??????????"service_id":?"temp",
??????????"properties":?{
??????????"event_time":?"20221018T131627Z"
當前設備上傳到云端服務器有一個溫度屬性字段temp,如果想轉(zhuǎn)發(fā)設備上傳的這個溫度字段,就可以這樣寫:
notify_data.body.services[0].properties.temp
后面的存儲目標字段,為了好區(qū)分,直接填temp即可。
如果設備還上傳了其他屬性字段也想轉(zhuǎn)發(fā),按照上面格式設置即可。
如果存儲數(shù)據(jù)時,想知道這個數(shù)據(jù)是那個產(chǎn)品,那個設備上傳的,也可以將設備ID和產(chǎn)品ID轉(zhuǎn)發(fā)存儲起來:格式如下。
notify_data.header.app_id??
notify_data.header.device_id
下面是我設置好,轉(zhuǎn)發(fā)存儲的字段:
確定后,點擊設置完成。
(3)測試規(guī)則
設置好之后,在設置轉(zhuǎn)發(fā)目標的頁面點擊測試。
輸入數(shù)據(jù)模板,然后點擊連通性測試。如果測試結(jié)果顯示成功,說明整體流程沒有問題了。
(4)啟用規(guī)則
設置完成后,點擊啟用規(guī)則。
(6)數(shù)據(jù)上報測試
為了驗證轉(zhuǎn)發(fā)規(guī)則是否生效,接下來使用MQTT客戶端多上報幾次數(shù)據(jù)到云平臺。
上傳之后,打開OBS存儲桶的控制臺頁面。打開轉(zhuǎn)發(fā)規(guī)則存儲的OBS桶。
找到存儲數(shù)據(jù)的文件,點擊下載。
下載下來,打開可以看到存儲的數(shù)據(jù):
到此,數(shù)據(jù)轉(zhuǎn)發(fā),存儲已經(jīng)成功了。
對于數(shù)據(jù)的可視化顯示,華為云提供了(Data Lake Visualization)一站式數(shù)據(jù)可視化平臺,數(shù)據(jù)可視化服務(DLV)可以從OBS文件讀取數(shù)據(jù)呈現(xiàn)為可視化報表,實現(xiàn)數(shù)據(jù)的可視化顯示。
下面是華為云的DLV大屏從OBS讀取數(shù)據(jù)顯示的流程:
當前我這里的需求是需要在本地自己設計界面顯示數(shù)據(jù),沒有采用華為云的DLV大屏,如果自己本地軟件需要顯示設備上傳的數(shù)據(jù),就需要使用華為云物聯(lián)網(wǎng)的平臺的應用側(cè)API接口,讀取設備上傳的數(shù)據(jù)進行,本地進行顯示;如果需要歷史數(shù)據(jù),可以讀取OBS存儲桶里存儲的數(shù)據(jù)進行顯示。
幫助文檔地址: https://support.huaweicloud.com/usermanual-iothub/iot_01_0045.html
應用側(cè)接口可以查詢發(fā)送指令給設備查詢屬性,也可以讀取設備的影子數(shù)據(jù)。
【1】查詢設備查詢: 這個是實時查詢,相當于應用側(cè)接口發(fā)送指令給在線設備,設備收到指令,將當前最新的數(shù)據(jù)再上傳。這個需要保證設備在線,離線是無法調(diào)用的。
【2】影子數(shù)據(jù): 影子數(shù)據(jù)相當于保存設備上傳的最新一次數(shù)據(jù)。 讀取讀取影子設備數(shù)據(jù),是不需要設備在線。
(1)接口URI地址
(2)請求參數(shù)說明
(3)響應參數(shù)
(4)請求示例
GET?https://{Endpoint}/v5/iot/{project_id}/devices/{device_id}/shadow
Content-Type:?application/json
(5)響應示例
Status Code: 200 OK
Content-Type:?application/json
??"device_id"?:?"40fe3542-f4cc-4b6a-98c3-61a49ba1acd4",
????"service_id"?:?"WaterMeter",
????????"temperature"?:?"60"
??????"event_time"?:?"20151212T121212Z"
????????"temperature"?:?"60"
??????"event_time"?:?"20151212T121212Z"
(6)錯誤碼
在線調(diào)試地址:https://apiexplorer.developer.huaweicloud.com/apiexplorer/debug?product=IoTDA&api=ShowDeviceShadow
下面是調(diào)試影子 數(shù)據(jù)查詢接口,查詢設備影子數(shù)據(jù): 右邊返回的是設備上傳的最新數(shù)據(jù)。
https://iotda.cn-north-4.myhuaweicloud.com/v5/iot/{project_id}/devices/{device_id}/shadow
?"X-Auth-Token":?"這個需要自己獲取",???
?"Content-Type":?"application/json"
使用API訪問華為云的所有服務接口,都需要填X-Subject-Token參數(shù),下面介紹步驟:
(1)創(chuàng)建一個新的IAM帳戶
鼠標懸停在右上角的用戶名稱上,彈出下拉框,選擇統(tǒng)一身份認證。
(2)選擇創(chuàng)建用戶
(3)使用調(diào)試接口測試獲取oken
調(diào)試接口地址: https://apiexplorer.developer.huaweicloud.com/apiexplorer/debug?product=IAM&api=KeystoneCreateUserTokenByPassword[1]
右邊響應頭里的X-Subject-Token就是獲取的token。
(4)上面的這些賬戶名稱從哪里獲取?
(5)請求地址和數(shù)據(jù)格式
獲取X-Subject-Token請求的地址: https://iam.cn-north-4.myhuaweicloud.com/v3/auth/tokens[2]
請求頭數(shù)據(jù):
??"User-Agent":?"API?Explorer",
??"X-Auth-Token":?"******",
??"Content-Type":?"application/json;charset=UTF-8"
請求體數(shù)據(jù):
?????????????"name":?"xxxxx"??//這里填當前主賬戶名稱
???????????"name":?"xxxx",??//這個新建的子賬戶名稱
???????????"password":?"xxxxx"????//這個是新建的子賬戶密碼
?????????"name":?"cn-north-4"
(6)代碼實現(xiàn)
?????QNetworkRequest?request;
?????requestUrl?=?QString("https://iam.%1.myhuaweicloud.com/v3/auth/tokens")
??????????????????.arg(SERVER_ID);
?????//requestUrl="http://10.0.0.6:8080";
?????request.setHeader(QNetworkRequest::ContentTypeHeader,?QVariant("application/json;charset=UTF-8"));
?????url.setUrl(requestUrl);
?????request.setUrl(url);
?????QString?text?=QString("{"auth":{"identity":{"methods":["password"],"password":"
?????"{"user":{"domain":?{"
?????""name":"%1"},"name":?"%2","password":?"%3"}}},"
?????""scope":{"project":{"name":"%4"}}}}")
?????????????.arg(MAIN_USER)
?????????????.arg(IAM_USER)
?????????????.arg(IAM_PASSWORD)
?????????????.arg(SERVER_ID);
?????manager->post(request,?text.toUtf8());
(1)這是請求代碼
void?Widget::Get_device_properties()
????QNetworkRequest?request;
????requestUrl?=?QString("https://iotda.%1.myhuaweicloud.com/v5/iot/%2/devices/%3/shadow")
?????????????????.arg(SERVER_ID)
????????????.arg(PROJECT_ID)
????????????.arg(device_id);
????request.setHeader(QNetworkRequest::ContentTypeHeader,?QVariant("application/json"));
????request.setRawHeader("X-Auth-Token",Token);
????url.setUrl(requestUrl);
????manager->get(request);
void?Widget::on_pushButton_update_device_clicked()
????Get_device_properties();
(2)這是請求一次返回的JSON數(shù)據(jù)
??"device_id":?"6353a8163ec34a6d03c8dfe5_dev1",
??????"service_id":?"temp",
????????"properties":?null,
????????"event_time":?null
????????"event_time":?"20221024T013607Z"
注意: 華為云、OneNet、騰訊IOT 等平臺規(guī)定接入的MQTT協(xié)議版本必須是3.1.1 。
在BC26里,需要執(zhí)行這行代碼配置MQTT協(xié)議版本為3.1.1
AT+QMTCFG="version",0,4
????GPIOC->CRL&=0xFFFFFFF0;
????GPIOC->CRL|=0x00000003;
????????char?*check_data?檢測返回的數(shù)據(jù)
u8?BC26_SendCmd(char?*cmd,char?*check_data)
???for(i=0;i<5;i++)?//測試的總次數(shù)
????memset(USART2_RX_BUFFER,0,sizeof(USART2_RX_BUFFER));
????USARTx_StringSend(USART2,cmd);?//發(fā)送指令
??????for(j=0;j<500;j++)?//等待的時間(ms單位)
??????????if(USART2_RX_FLAG)
??????????????USART2_RX_BUFFER[USART2_RX_CNT]='\0';
??????????????if(strstr((char*)USART2_RX_BUFFER,check_data))
??????????????????return?0;
??????????????else?break;
??????????delay_ms(30);?//一次的時間
????if(BC26_SendCmd("AT\r\n","OK"))
????????USART1_Printf("BC26模塊不存在.\r\n");
????????USART1_Printf("BC26模塊正常!\r\n");
????if(BC26_SendCmd("AT+CIMI\r\n","OK"))
????????USART1_Printf("模塊未插卡.\r\n");
????????USART1_Printf("卡已經(jīng)插好.\r\n");
????if(BC26_SendCmd("AT+CGATT=1\r\n","OK"))
????????USART1_Printf("配置:網(wǎng)絡激活失敗.\r\n");
????????USART1_Printf("配置:網(wǎng)絡激活成功.\r\n");
????if(BC26_SendCmd("AT+CGATT?\r\n","OK"))
????????USART1_Printf("狀態(tài):網(wǎng)絡激活失敗.\r\n");
????????USART1_Printf("狀態(tài):網(wǎng)絡激活成功.\r\n");
????if(BC26_SendCmd("AT+CSQ\r\n","OK"))
????????USART1_Printf("查詢信號質(zhì)量失敗.\r\n");
????????USART1_Printf("信號質(zhì)量:%s\r\n",USART2_RX_BUFFER);
//????if(BC26_SendCmd("AT+QGNSSC=1\r\n","OK"))
//????????USART1_Printf("激活GPS定位失敗.\r\n");
//????????USART1_Printf("激活GPS定位成功.\r\n");
//????if(BC26_SendCmd("AT+QGNSSAGPS=1\r\n","OK"))
//????????USART1_Printf("開啟AGPS定位失敗.\r\n");
//????????USART1_Printf("開啟AGPS定位成功.\r\n");
//????if(BC26_SendCmd("AT+CGPADDR=1\r\n","OK"))
//????????USART1_Printf("激活GPRS場景失敗.\r\n");
//????????USART1_Printf("激活GPRS場景成功.\r\n");
????if(BC26_SendCmd("AT+CEREG?\r\n","+CEREG:?0,1"))
????????USART1_Printf("網(wǎng)絡注冊狀態(tài):失敗.\r\n");
????????USART1_Printf("網(wǎng)絡注冊狀態(tài):成功.\r\n");
char?BC26_SEND_BUFF[500];
int?BC26_MQTT_Connect(void)
?????USART1_Printf("正在關(guān)閉之前的連接...\r\n");
????BC26_SendCmd("AT+QMTCLOSE=0\r\n","OK");
????BC26_SendCmd("AT+QMTCONN?\r\n","OK");
????USART1_Printf("正在連接MQTT服務器..\r\n");
????sprintf(BC26_SEND_BUFF,"AT+QMTOPEN=0,\"%s\",%s\r\n",MQTT_SERVER_ADDR,MQTT_SERVER_PORT);
????if(BC26_SendCmd(BC26_SEND_BUFF,"OK"))
????????USART1_Printf("MQTT服務器連接失敗:%s\r\n",BC26_SEND_BUFF);
????????USART1_Printf("MQTT服務器連接成功.\r\n");
????USART1_Printf("正在登錄MQTT服務器...\r\n");
????sprintf(BC26_SEND_BUFF,"AT+QMTCONN=0,\"%s\",\"%s\",\"%s\"\r\n",MQTT_CLIENT_ID,MQTT_USERNAME,MQTT_PASSWORD);
????if(BC26_SendCmd(BC26_SEND_BUFF,"OK"))
????????USART1_Printf("MQTT服務器登錄失敗:%s\r\n",BC26_SEND_BUFF);
????????USART1_Printf("MQTT服務器登錄成功.\r\n");
????USART1_Printf("正在訂閱主題...\r\n");
????sprintf(BC26_SEND_BUFF,"AT+QMTSUB=0,1,\"%s\",2\r\n",MQTT_TOPIC_SUB_GET);
????if(BC26_SendCmd(BC26_SEND_BUFF,"OK"))
????????USART1_Printf("MQTT主題訂閱失敗:%s\r\n",BC26_SEND_BUFF);
????????USART1_Printf("MQTT主題訂閱成功.\r\n");
int?MQTT_PublishTheme(char?*text)
????sprintf(BC26_SEND_BUFF,"AT+QMTPUB=0,0,0,0,\"%s\"\r\n",MQTT_TOPIC_SUB_SET);
????if(BC26_SendCmd(BC26_SEND_BUFF,">"))
????????USART1_Printf("發(fā)布主題等待輸入失敗:%s\r\n",BC26_SEND_BUFF);
????USARTx_StringSend(USART2,text);?????//發(fā)送主題內(nèi)容
????if(BC26_SendCmd(send_buf,"OK"))
????????USART1_Printf("發(fā)布主題內(nèi)容失敗:%s\r\n",BC26_SEND_BUFF);
????????return?2;?//發(fā)送結(jié)束符號
????????USART1_Printf("發(fā)布主題內(nèi)容成功.\r\n");
?????USART1_Printf("發(fā)布主題內(nèi)容:%s\r\n",text);
int?MQTT_SendAttribute(char?*text,char?*request_id)
????sprintf(BC26_SEND_BUFF,"AT+QMTPUB=0,0,0,0,\"%s%s\"\r\n",MQTT_TOPIC_SUB_SET_RUN,request_id);
????if(BC26_SendCmd(BC26_SEND_BUFF,">"))
????????USART1_Printf("(響應)發(fā)布主題等待輸入失敗:%s\r\n",BC26_SEND_BUFF);
????USARTx_StringSend(USART2,text);?????//發(fā)送主題內(nèi)容
????if(BC26_SendCmd(send_buf,"OK"))
????????USART1_Printf("(響應)發(fā)布主題內(nèi)容失敗:%s\r\n",BC26_SEND_BUFF);
????????return?2;?//發(fā)送結(jié)束符號
????????USART1_Printf("(響應)發(fā)布主題內(nèi)容成功.\r\n");
?????USART1_Printf("(響應)發(fā)布主題內(nèi)容:%s\r\n",text);
????????double?*Longitude??:經(jīng)度
????????double?*latitude???:緯度
返回值:?0表示定位成功,1表示數(shù)據(jù)接收失敗,2表示定位失敗
u8?BC26_GetGPS_Data(double?*Longitude,double?*latitude)
????if(BC26_SendCmd("AT+QGNSSRD=\"NMEA/RMC\"\r\n",?"OK\r\n"))return?1;
????if(GPS_GNRMC_Decoding((char?*)USART2_RX_BUFFER,Longitude,latitude))return?2;
????if(BC26_SendCmd("AT+QGNSSC?\r\n","+QGNSSC:?1"))?
????????if(BC26_SendCmd("AT+QGNSSC=1\r\n","OK\r\n"))
????????????USART1_Printf("開啟GPS功能失敗.\r\n");
????????????return?1;??//GPS功能啟動失敗
????????????USART1_Printf("開啟GPS功能成功.\r\n");
https://apiexplorer.developer.huaweicloud.com/apiexplorer/debug?product=IAM&api=KeystoneCreateUserTokenByPassword: https://apiexplorer.developer.huaweicloud.com/apiexplorer/debug?product=IAM&api=KeystoneCreateUserTokenByPassword
[2]https://iam.cn-north-4.myhuaweicloud.com/v3/auth/tokens: https://iam.cn-north-4.myhuaweicloud.com/v3/auth/tokens
推薦閱讀
01 |加入嵌入式交流群 |
02 |嵌入式資源獲取 |
03 |STM32中斷優(yōu)先級詳解 |
04 |STM32下載程序新思路--使用串口下載程序 |

