Öğretici - Cihaz SDK'sı kullanmadan IoT cihaz istemcisi geliştirmek için MQTT kullanma

Mümkünse IoT cihaz istemcilerinizi oluşturmak için Azure IoT Cihaz SDK'larından birini kullanmanız gerekir. Ancak bellek kısıtlanmış cihaz kullanma gibi senaryolarda IoT hub'ınızla iletişim kurmak için bir MQTT kitaplığı kullanmanız gerekebilir.

Bu öğreticideki örnekler Eclipse Mosquitto MQTT kitaplığını kullanır.

Bu öğreticide aşağıdakilerin nasıl yapılacağını öğreneceksiniz:

  • C dili cihaz istemci örnek uygulamalarını oluşturun.
  • Telemetri göndermek için MQTT kitaplığını kullanan bir örnek çalıştırın.
  • IoT hub'ınızdan gönderilen buluttan cihaza iletiyi işlemek için MQTT kitaplığını kullanan bir örnek çalıştırın.
  • Cihazdaki cihaz ikizini yönetmek için MQTT kitaplığını kullanan bir örnek çalıştırın.

Bu öğreticideki adımları tamamlamak için bir Windows veya Linux geliştirme makinesi kullanabilirsiniz.

Azure aboneliğiniz yoksa başlamadan önce ücretsiz bir hesap oluşturun.

Önkoşullar

Ortamınızı Azure CLI’ye hazırlama

  • Azure Cloud Shell'de Bash ortamını kullanın. Daha fazla bilgi için bkz . Azure Cloud Shell'de Bash için hızlı başlangıç.

  • CLI başvuru komutlarını yerel olarak çalıştırmayı tercih ediyorsanız Azure CLI'yı yükleyin . Windows veya macOS üzerinde çalışıyorsanız Azure CLI’yi bir Docker kapsayıcısında çalıştırmayı değerlendirin. Daha fazla bilgi için bkz . Docker kapsayıcısında Azure CLI'yi çalıştırma.

    • Yerel yükleme kullanıyorsanız az login komutunu kullanarak Azure CLI ile oturum açın. Kimlik doğrulama işlemini tamamlamak için terminalinizde görüntülenen adımları izleyin. Diğer oturum açma seçenekleri için bkz . Azure CLI ile oturum açma.

    • İstendiğinde, ilk kullanımda Azure CLI uzantısını yükleyin. Uzantılar hakkında daha fazla bilgi için bkz. Azure CLI ile uzantıları kullanma.

    • Yüklü sürümü ve bağımlı kitaplıkları bulmak için az version komutunu çalıştırın. En son sürüme yükseltmek için az upgrade komutunu çalıştırın.

Geliştirme makinesi önkoşulları

Windows kullanıyorsanız:

  1. Visual Studio'yu (Community, Professional veya Enterprise) yükleyin. C++ iş yüküyle Masaüstü geliştirmeyi etkinleştirdiğinizden emin olun.

  2. CMake'yi yükleyin. Tüm kullanıcılar için sistem PATH'sine CMake ekle seçeneğini etkinleştirin.

  3. Mosquitto'nun x64 sürümünü yükleyin.

Linux kullanıyorsanız:

  1. Derleme araçlarını yüklemek için aşağıdaki komutu çalıştırın:

    sudo apt install cmake g++
    
  2. Mosquitto istemci kitaplığını yüklemek için aşağıdaki komutu çalıştırın:

    sudo apt install libmosquitto-dev
    

Ortamınızı ayarlama

Henüz bir IoT hub'ına sahip değilseniz adlı mqtt-sample-rgkaynak grubunda serbest katmanlı bir IoT hub'ı oluşturmak için aşağıdaki komutları çalıştırın. komutu, oluşturulacak IoT hub'ının adı için örnek olarak adını kullanır my-hub . IoT hub'ınız için yerine kullanılacak my-hubbenzersiz bir ad seçin:

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

IoT hub'ınızın adını not alın, daha sonra ihtiyacınız olacak.

IoT hub'ınıza bir cihaz kaydedin. Aşağıdaki komut adlı bir ioT hub'ına adlı mqtt-dev-01my-hubbir cihazı kaydeder. IoT hub'ınızın adını kullandığınızdan emin olun:

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

IoT hub'ınıza cihaz erişimi veren bir SAS belirteci oluşturmak için aşağıdaki komutu kullanın. IoT hub'ınızın adını kullandığınızdan emin olun:

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

Komut çıktılarının SAS belirtecini daha sonra ihtiyacınız olduğu gibi not edin. SAS belirteci şuna benzer: SharedAccessSignature sr=my-hub.azure-devices.net%2Fdevices%2Fmqtt-dev-01&sig=%2FnM...sNwtnnY%3D&se=1677855761

İpucu

Varsayılan olarak SAS belirteci 60 dakika geçerlidir. --du 7200 Önceki komuttaki seçenek, belirteç süresini iki saate uzatır. Kullanmaya hazır olmadan önce süresi dolarsa yeni bir tane oluşturun. Ayrıca daha uzun bir süreye sahip bir belirteç de oluşturabilirsiniz. Daha fazla bilgi edinmek için bkz . az iot hub generate-sas-token.

Örnek depoyu kopyalama

Örnek depoyu yerel makinenizde uygun bir konuma kopyalamak için aşağıdaki komutu kullanın:

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

Depo şunları da içerir:

  • Kitaplığı kullanan paho-mqtt bir Python örneği.
  • Cli kullanarak mosquitto_pub IoT hub'ınızla etkileşim kurma yönergeleri.

C örneklerini oluşturma

Örneği derlemeden önce IoT hub'ını ve cihaz ayrıntılarını eklemeniz gerekir. Kopyalanan IoTMQTTSample deposunda mosquitto/src/config.h dosyasını açın. IoT hub'ınızın adını, cihaz kimliğini ve SAS belirtecini aşağıdaki gibi ekleyin. IoT hub'ınızın adını kullandığınızdan emin olun:

// 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"

Not

IoTHubRootCA.crt.pem dosyası, TLS bağlantısı için CA kök sertifikalarını içerir.

Mosquitto/src/config.h dosyasındaki değişiklikleri kaydedin.

Örnekleri oluşturmak için kabuğunuzda aşağıdaki komutları çalıştırın:

cd mosquitto
cmake -Bbuild
cmake --build build

Linux'ta ikili dosyalar mosquitto klasörünün altındaki ./build klasöründedir.

Windows'da ikili dosyalar mosquitto klasörünün altındaki .\build\Debug klasöründedir.

Telemetri gönderme

mosquitto_telemetry örneği, MQTT kitaplığını kullanarak IoT hub'ınıza cihazdan buluta telemetri iletisi göndermeyi gösterir.

Örnek uygulamayı çalıştırmadan önce aşağıdaki komutu çalıştırarak IoT hub'ınızın olay izleyicisini başlatın. IoT hub'ınızın adını kullandığınızdan emin olun:

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

mosquitto_telemetry örneğini çalıştırın. Örneğin, Linux'ta:

./build/mosquitto_telemetry

, az iot hub monitor-events cihaz tarafından gönderilen yükü gösteren aşağıdaki çıkışı oluşturur:

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

Artık olay izleyicisini durdurabilirsiniz.

Kodu gözden geçirin

Aşağıdaki kod parçacıkları mosquitto/src/mosquitto_telemetry.cpp dosyasından alınır.

Aşağıdaki deyimler, bağlantı bilgilerini ve telemetri iletisini göndermek için kullandığınız MQTT konusunun adını tanımlar:

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

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

işlevi, main IoT hub'ınızla kimlik doğrulaması yapmak için kullanıcı adını ve parolayı ayarlar. Parola, cihazınız için oluşturduğunuz SAS belirtecidir:

mosquitto_username_pw_set(mosq, USERNAME, SAS_TOKEN);

Örnek, IoT hub'ınıza telemetri iletisi göndermek için MQTT konusunu kullanır:

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");

Daha fazla bilgi edinmek için bkz . Cihazdan buluta ileti gönderme.

Buluttan cihaza ileti alma

mosquitto_subscribe örneği, MQTT kitaplığını kullanarak MQTT konularına abone olmayı ve IoT hub'ınızdan buluttan cihaza ileti almayı gösterir.

mosquitto_subscribe örneğini çalıştırın. Örneğin, Linux'ta:

./build/mosquitto_subscribe

IoT hub'ınızdan buluttan cihaza ileti göndermek için aşağıdaki komutu çalıştırın. IoT hub'ınızın adını kullandığınızdan emin olun:

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

mosquitto_subscribe çıktısı aşağıdaki örneğe benzer:

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

Kodu gözden geçirin

Aşağıdaki kod parçacıkları mosquitto/src/mosquitto_subscribe.cpp dosyasından alınır.

Aşağıdaki deyim, cihazın buluttan cihaza iletileri almak için kullandığı konu filtresini tanımlar. # çok düzeyli bir joker karakterdir:

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

İşlevmosquitto_message_callback_set, IoT hub'ınızdan main gönderilen iletileri işlemek için geri çağırma ayarlamak için işlevini ve tüm iletilere abone olmak için işlevini kullanırmosquitto_subscribe. Aşağıdaki kod parçacığı geri çağırma işlevini gösterir:

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");
    }
}

Daha fazla bilgi edinmek için bkz . Buluttan cihaza iletileri almak için MQTT kullanma.

Cihaz ikizlerini güncelleştirme

mosquitto_device_twin örneği, bir cihaz ikizi içinde bildirilen özelliği ayarlamayı ve ardından özelliği geri okumayı gösterir.

mosquitto_device_twin örneğini çalıştırın. Örneğin, Linux'ta:

./build/mosquitto_device_twin

mosquitto_device_twin çıktısı aşağıdaki örneğe benzer:

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.

Kodu gözden geçirin

Aşağıdaki kod parçacıkları mosquitto/src/mosquitto_device_twin.cpp dosyasından alınır.

Aşağıdaki deyimler cihazın cihaz ikizi güncelleştirmelerine abone olmak, cihaz ikizini okumak ve cihaz ikizini güncelleştirmek için kullandığı konuları tanımlar:

#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"

İşlevmosquitto_connect_callback_set, IoT hub'ınızdan main gönderilen iletileri işlemek üzere bir geri çağırma ayarlamak için işlevini kullanır ve konuya abone olmak için $iothub/twin/res/# işlevini kullanırmosquitto_subscribe.

Aşağıdaki kod parçacığı, cihaz ikizinde connect_callback bildirilen bir özelliği ayarlamak için kullanan mosquitto_publish işlevi gösterir. Cihaz, iletiyi konu başlığında $iothub/twin/PATCH/properties/reported/?$rid=%d yayımlar. %d Cihaz konu başlığına her ileti yayımlayışında değer artırılır:

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 ...  
}

Cihaz konuya abone $iothub/twin/res/# olur ve IoT hub'ınızdan message_callback bir ileti aldığında işlev bunu işler. Örneği çalıştırdığınızda işlev message_callback iki kez çağrılır. Cihaz ilk kez IoT hub'ından bildirilen özellik güncelleştirmesi için bir yanıt alır. Cihaz daha sonra cihaz ikizini istemektedir. İkinci kez cihaz istenen cihaz ikizini alır. Aşağıdaki kod parçacığı işlevi gösterir 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
    }
}

Daha fazla bilgi edinmek için bkz . Cihaz ikizi bildirilen özelliğini güncelleştirmek için MQTT kullanma ve Cihaz ikizi özelliğini almak için MQTT kullanma.

Kaynakları temizleme

Daha fazla cihaz geliştirici makalesine devam etmek istiyorsanız, bu makalede kullandığınız kaynakları tutabilir ve yeniden kullanabilirsiniz. Aksi takdirde, daha fazla ücret tahsil edilmemesi için bu makalede oluşturduğunuz kaynakları silebilirsiniz.

Aşağıdaki Azure CLI komutuyla kaynak grubunun tamamını silerek hem hub'ı hem de kayıtlı cihazı aynı anda silebilirsiniz. Bu kaynaklar bir kaynak grubunu saklamak istediğiniz diğer kaynaklarla paylaşıyorsa bu komutu kullanmayın.

az group delete --name <YourResourceGroupName>

Yalnızca IoT hub'ını silmek için Azure CLI kullanarak aşağıdaki komutu çalıştırın:

az iot hub delete --name <YourIoTHubName>

Yalnızca IoT hub'ınıza kaydettiğiniz cihaz kimliğini silmek için Azure CLI kullanarak aşağıdaki komutu çalıştırın:

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

Kopyalanan örnek dosyaları geliştirme makinenizden de kaldırmak isteyebilirsiniz.

Sonraki adımlar

IoT Hub ile iletişim kurmak için Mosquitto MQTT kitaplığını kullanmayı öğrendiğinize göre, önerilen bir sonraki adım gözden geçirmektir: