مشاركة عبر


البرنامج التعليمي - استخدام MQTT لتطوير عميل جهاز IoT دون استخدام جهاز SDK

يجب عليك استخدام أحد Azure IoT Device SDKs لإنشاء عملاء جهاز IoT إذا كان ذلك ممكنا. ومع ذلك، في وحدات السيناريو مثل استخدام جهاز مقيد بالذاكرة، قد تحتاج إلى استخدام مكتبة MQTT للاتصال بمركز IoT.

تستخدم العينات في هذا البرنامج التعليمي مكتبة Eclipse Mosquitto MQTT.

في هذا البرنامج التعليمي، تتعلم كيفية:

  • إنشاء تطبيقات نموذج عميل جهاز لغة C.
  • قم بتشغيل عينة تستخدم مكتبة MQTT لإرسال بيانات تتبع الاستخدام.
  • قم بتشغيل عينة تستخدم مكتبة MQTT لمعالجة رسالة من سحابة إلى جهاز تم إرسالها من مركز IoT الخاص بك.
  • قم بتشغيل عينة تستخدم مكتبة MQTT لإدارة الجهاز المزدوج على الجهاز.

يمكنك استخدام جهاز تطوير Windows أو Linux لإكمال الخطوات الواردة في هذا البرنامج التعليمي.

في حال لم يكن لديك اشتراك Azure، فأنشئ حساباً مجانيّاً قبل البدء.

المتطلبات الأساسية

إعداد البيئة الخاصة بك لـ Azure CLI

المتطلبات الأساسية لجهاز التطوير

إذا كنت تستخدم Windows:

  1. تثبيت Visual Studio (Community أو Professional أو Enterprise) . تأكد من تمكين تطوير سطح المكتب مع حمل عمل C++‎ .

  2. قم بتثبيت CMake. قم بتمكين الخيار Add CMake to the system PATH لجميع المستخدمين .

  3. قم بتثبيت إصدار x64 من Mosquitto.

إذا كنت تستخدم Linux:

  1. قم بتشغيل الأمر التالي لتثبيت أدوات الإنشاء:

    sudo apt install cmake g++
    
  2. قم بتشغيل الأمر التالي لتثبيت مكتبة عميل Mosquitto:

    sudo apt install libmosquitto-dev
    

إعداد بيئتك

إذا لم يكن لديك مركز IoT بالفعل، فقم بتشغيل الأوامر التالية لإنشاء مركز IoT من الطبقة الحرة في مجموعة موارد تسمى mqtt-sample-rg. يستخدم الأمر الاسم my-hub كمثال لاسم مركز IoT المراد إنشاؤه. اختر اسماً فريداً لمركز IoT الخاص بك لاستخدامه بدلاً من my-hub:

az group create --name mqtt-sample-rg --location eastus
az iot hub create --name my-hub --resource-group mqtt-sample-rg --sku F1 

دون اسم مركز IoT الخاص بك، فأنت بحاجة إليه لاحقا.

تسجيل جهاز في مركز IoT الخاص بك. يسجل الأمر التالي جهازا يسمى mqtt-dev-01 في مركز IoT يسمى my-hub. تأكد من استخدام اسم مركز IoT الخاص بك:

az iot hub device-identity create --hub-name my-hub --device-id mqtt-dev-01

استخدم الأمر التالي لإنشاء رمز SAS المميز الذي يمنح الجهاز حق الوصول إلى مركز IoT الخاص بك. تأكد من استخدام اسم مركز IoT الخاص بك:

az iot hub generate-sas-token --device-id mqtt-dev-01 --hub-name my-hub --du 7200

دون ملاحظة عن رمز SAS المميز إخراجات الأمر كما تحتاج إليه لاحقا. يبدو رمز SAS المميز مثل SharedAccessSignature sr=my-hub.azure-devices.net%2Fdevices%2Fmqtt-dev-01&sig=%2FnM...sNwtnnY%3D&se=1677855761

تلميح

بشكل افتراضي، يكون رمز SAS المميز صالحا لمدة 60 دقيقة. يوسع --du 7200 الخيار في الأمر السابق مدة الرمز المميز إلى ساعتين. إذا انتهت صلاحيته قبل أن تكون مستعدا لاستخدامه، فنشئ واحدا جديدا. يمكنك أيضا إنشاء رمز مميز لمدة أطول. لمعرفة المزيد، راجع az iot hub generate-sas-token.

استنساخ مستودع العينة

استخدم الأمر التالي لنسخ مستودع العينة إلى موقع مناسب على جهازك المحلي:

git clone https://github.com/Azure-Samples/IoTMQTTSample.git

يتضمن المستودع أيضا ما يلي:

  • نموذج Python يستخدم المكتبة paho-mqtt .
  • إرشادات لاستخدام mosquitto_pub CLI للتفاعل مع مركز IoT الخاص بك.

إنشاء عينات C

قبل إنشاء العينة، تحتاج إلى إضافة مركز IoT وتفاصيل الجهاز. في مستودع IoTMQTTSample المستنسخ، افتح ملف mosquitto/src/config.h . أضف اسم مركز IoT ومعرف الجهاز ورمز SAS المميز كما يلي. تأكد من استخدام اسم مركز IoT الخاص بك:

// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

#define IOTHUBNAME "my-hub"
#define DEVICEID   "mqtt-dev-01"
#define SAS_TOKEN  "SharedAccessSignature sr=my-hub.azure-devices.net%2Fdevices%2Fmqtt-dev-01&sig=%2FnM...sNwtnnY%3D&se=1677855761"

#define CERTIFICATEFILE CERT_PATH "IoTHubRootCA.crt.pem"

إشعار

يتضمن ملف IoTHubRootCA.crt.pem شهادات جذر CA لاتصال TLS.

احفظ التغييرات في ملف mosquitto/src/config.h .

لإنشاء العينات، قم بتشغيل الأوامر التالية في shell الخاص بك:

cd mosquitto
cmake -Bbuild
cmake --build build

في Linux، توجد الثنائيات في مجلد ./build أسفل المجلد mosquitto .

في Windows، توجد الثنائيات في المجلد .\build\Debug أسفل المجلد mosquitto .

إرسال بيانات تتبع الاستخدام

يوضح نموذج mosquitto_telemetry كيفية إرسال رسالة بيانات تتبع الاستخدام من جهاز إلى سحابة إلى مركز IoT باستخدام مكتبة MQTT.

قبل تشغيل نموذج التطبيق، قم بتشغيل الأمر التالي لبدء مراقبة الحدث لمركز IoT الخاص بك. تأكد من استخدام اسم مركز IoT الخاص بك:

az iot hub monitor-events --hub-name my-hub

قم بتشغيل نموذج mosquitto_telemetry. على سبيل المثال، على Linux:

./build/mosquitto_telemetry

az iot hub monitor-events ينشئ الإخراج التالي الذي يظهر الحمولة المرسلة من قبل الجهاز:

Starting event monitor, use ctrl-c to stop...
{
    "event": {
        "origin": "mqtt-dev-01",
        "module": "",
        "interface": "",
        "component": "",
        "payload": "Bonjour MQTT from Mosquitto"
    }
}

يمكنك الآن إيقاف مراقبة الحدث.

مراجعة الرمز

يتم أخذ القصاصات البرمجية التالية من ملف mosquitto/src/mosquitto_telemetry.cpp .

تحدد العبارات التالية معلومات الاتصال واسم موضوع MQTT الذي تستخدمه لإرسال رسالة بيانات تتبع الاستخدام:

#define HOST IOTHUBNAME ".azure-devices.net"
#define PORT 8883
#define USERNAME HOST "/" DEVICEID "/?api-version=2020-09-30"

#define TOPIC "devices/" DEVICEID "/messages/events/"

تعين main الدالة اسم المستخدم وكلمة المرور للمصادقة مع مركز IoT الخاص بك. كلمة المرور هي رمز SAS المميز الذي أنشأته لجهازك:

mosquitto_username_pw_set(mosq, USERNAME, SAS_TOKEN);

يستخدم النموذج موضوع MQTT لإرسال رسالة بيانات تتبع الاستخدام إلى مركز IoT الخاص بك:

int msgId  = 42;
char msg[] = "Bonjour MQTT from Mosquitto";

// once connected, we can publish a Telemetry message
printf("Publishing....\r\n");
rc = mosquitto_publish(mosq, &msgId, TOPIC, sizeof(msg) - 1, msg, 1, true);
if (rc != MOSQ_ERR_SUCCESS)
{
    return mosquitto_error(rc);
}
printf("Publish returned OK\r\n");

لمعرفة المزيد، راجع إرسال رسائل من جهاز إلى سحابة.

تلقي رسالة من سحابة إلى جهاز

يوضح نموذج mosquitto_subscribe كيفية الاشتراك في موضوعات MQTT وتلقي رسالة من السحابة إلى الجهاز من مركز IoT باستخدام مكتبة MQTT.

تشغيل نموذج mosquitto_subscribe. على سبيل المثال، على Linux:

./build/mosquitto_subscribe

قم بتشغيل الأمر التالي لإرسال رسالة من سحابة إلى جهاز من مركز IoT. تأكد من استخدام اسم مركز IoT الخاص بك:

az iot device c2d-message send --hub-name my-hub --device-id mqtt-dev-01 --data "hello world"

يبدو الإخراج من mosquitto_subscribe مثل المثال التالي:

Waiting for C2D messages...
C2D message 'hello world' for topic 'devices/mqtt-dev-01/messages/devicebound/%24.mid=d411e727-...f98f&%24.to=%2Fdevices%2Fmqtt-dev-01%2Fmessages%2Fdevicebound&%24.ce=utf-8&iothub-ack=none'
Got message for devices/mqtt-dev-01/messages/# topic

مراجعة الرمز

يتم أخذ القصاصات البرمجية التالية من ملف mosquitto/src/mosquitto_subscribe.cpp .

تحدد العبارة التالية عامل تصفية الموضوع الذي يستخدمه الجهاز لتلقي رسائل السحابة إلى الجهاز. هو # حرف بدل متعدد المستويات:

#define DEVICEMESSAGE "devices/" DEVICEID "/messages/#"

main تستخدم الدالة الدالة mosquitto_message_callback_set لتعيين رد اتصال لمعالجة الرسائل المرسلة من مركز IoT الخاص بك وتستخدم الدالة mosquitto_subscribe للاشتراك في جميع الرسائل. تعرض القصاصة البرمجية التالية دالة رد الاتصال:

void message_callback(struct mosquitto* mosq, void* obj, const struct mosquitto_message* message)
{
    printf("C2D message '%.*s' for topic '%s'\r\n", message->payloadlen, (char*)message->payload, message->topic);

    bool match = 0;
    mosquitto_topic_matches_sub(DEVICEMESSAGE, message->topic, &match);

    if (match)
    {
        printf("Got message for " DEVICEMESSAGE " topic\r\n");
    }
}

لمعرفة المزيد، راجع استخدام MQTT لتلقي رسائل من السحابة إلى الجهاز.

تحديث توأم الجهاز

يوضح نموذج mosquitto_device_twin كيفية تعيين خاصية تم الإبلاغ عنها في جهاز مزدوج ثم قراءة الخاصية مرة أخرى.

تشغيل نموذج mosquitto_device_twin. على سبيل المثال، على Linux:

./build/mosquitto_device_twin

يبدو الإخراج من mosquitto_device_twin مثل المثال التالي:

Setting device twin reported properties....
Device twin message '' for topic '$iothub/twin/res/204/?$rid=0&$version=2'
Setting device twin properties SUCCEEDED.

Getting device twin properties....
Device twin message '{"desired":{"$version":1},"reported":{"temperature":32,"$version":2}}' for topic '$iothub/twin/res/200/?$rid=1'
Getting device twin properties SUCCEEDED.

مراجعة الرمز

يتم أخذ القصاصات البرمجية التالية من ملف mosquitto/src/mosquitto_device_twin.cpp .

تحدد العبارات التالية الموضوعات التي يستخدمها الجهاز للاشتراك في تحديثات الجهاز المزدوجة، وقراءة الجهاز المزدوج، وتحديث الجهاز المزدوج:

#define DEVICETWIN_SUBSCRIPTION  "$iothub/twin/res/#"
#define DEVICETWIN_MESSAGE_GET   "$iothub/twin/GET/?$rid=%d"
#define DEVICETWIN_MESSAGE_PATCH "$iothub/twin/PATCH/properties/reported/?$rid=%d"

main تستخدم الدالة الدالة mosquitto_connect_callback_set لتعيين رد اتصال لمعالجة الرسائل المرسلة من مركز IoT الخاص بك وتستخدم الدالة mosquitto_subscribe للاشتراك في $iothub/twin/res/# الموضوع.

تعرض القصاصة البرمجية التالية الدالة connect_callback التي تستخدم mosquitto_publish لتعيين خاصية تم الإبلاغ عنها في الجهاز المزدوج. ينشر الجهاز الرسالة إلى $iothub/twin/PATCH/properties/reported/?$rid=%d الموضوع. %d يتم زيادة القيمة في كل مرة ينشر فيها الجهاز رسالة إلى الموضوع:

void connect_callback(struct mosquitto* mosq, void* obj, int result)
{
    // ... other code ...  

    printf("\r\nSetting device twin reported properties....\r\n");

    char msg[] = "{\"temperature\": 32}";
    char mqtt_publish_topic[64];
    snprintf(mqtt_publish_topic, sizeof(mqtt_publish_topic), DEVICETWIN_MESSAGE_PATCH, device_twin_request_id++);

    int rc = mosquitto_publish(mosq, NULL, mqtt_publish_topic, sizeof(msg) - 1, msg, 1, true);
    if (rc != MOSQ_ERR_SUCCESS)

    // ... other code ...  
}

يشترك الجهاز في $iothub/twin/res/# الموضوع وعندما يتلقى رسالة من مركز IoT الخاص بك، تعالجه الدالة message_callback . عند تشغيل النموذج، يتم استدعاء الدالة message_callback مرتين. في المرة الأولى، يتلقى الجهاز استجابة من مركز IoT لتحديث الخاصية المبلغ عنها. ثم يطلب الجهاز توأم الجهاز. في المرة الثانية، يتلقى الجهاز توأم الجهاز المطلوب. تعرض القصاصة البرمجية التالية الدالة message_callback :

void message_callback(struct mosquitto* mosq, void* obj, const struct mosquitto_message* message)
{
    printf("Device twin message '%.*s' for topic '%s'\r\n", message->payloadlen, (char*)message->payload, message->topic);

    const char patchTwinTopic[] = "$iothub/twin/res/204/?$rid=0";
    const char getTwinTopic[]   = "$iothub/twin/res/200/?$rid=1";

    if (strncmp(message->topic, patchTwinTopic, sizeof(patchTwinTopic) - 1) == 0)
    {
        // Process the reported property response and request the device twin
        printf("Setting device twin properties SUCCEEDED.\r\n\r\n");

        printf("Getting device twin properties....\r\n");

        char msg[] = "{}";
        char mqtt_publish_topic[64];
        snprintf(mqtt_publish_topic, sizeof(mqtt_publish_topic), DEVICETWIN_MESSAGE_GET, device_twin_request_id++);

        int rc = mosquitto_publish(mosq, NULL, mqtt_publish_topic, sizeof(msg) - 1, msg, 1, true);
        if (rc != MOSQ_ERR_SUCCESS)
        {
            printf("Error: %s\r\n", mosquitto_strerror(rc));
        }
    }
    else if (strncmp(message->topic, getTwinTopic, sizeof(getTwinTopic) - 1) == 0)
    {
        // Process the device twin response and stop the client
        printf("Getting device twin properties SUCCEEDED.\r\n\r\n");

        mosquitto_loop_stop(mosq, false);
        mosquitto_disconnect(mosq); // finished, exit program
    }
}

لمعرفة المزيد، راجع استخدام MQTT لتحديث خاصية الجهاز المزدوج المبلغ عنها واستخدام MQTT لاسترداد خاصية توأم الجهاز.

تنظيف الموارد

إذا كنت تخطط لمتابعة المزيد من مقالات مطوري الأجهزة، يمكنك الاحتفاظ بالموارد التي استخدمتها في هذه المقالة وإعادة استخدامها. وإلا، يمكنك حذف الموارد التي أنشأتها في هذه المقالة لتجنب المزيد من الرسوم.

يمكنك حذف كل من الموزع والجهاز المسجل مرة واحدة عن طريق حذف مجموعة الموارد بأكملها باستخدام أمر Azure CLI التالي. لا تستخدم هذا الأمر إذا كانت هذه الموارد تشارك مجموعة موارد مع موارد أخرى تريد الاحتفاظ بها.

az group delete --name <YourResourceGroupName>

لحذف مركز IoT فقط، تشغّل الأمر التالي باستخدام Azure CLI:

az iot hub delete --name <YourIoTHubName>

لحذف هوية الجهاز التي قمت بتسجيلها مع لوحة الوصل الخاصة بك، IoT فقط، قم بتشغيل الأمر التالي باستخدام Azure CLI:

az iot hub device-identity delete --hub-name <YourIoTHubName> --device-id <YourDeviceID>

قد ترغب أيضًا في إزالة ملفات العينات المستنسخة من جهاز التطوير.

الخطوات التالية

الآن بعد أن تعلمت كيفية استخدام مكتبة Mosquitto MQTT للتواصل مع IoT Hub، فإن الخطوة التالية المقترحة هي مراجعة: