Uw apparaat verbinden met de vooraf geconfigureerde oplossing voor externe bewaking (Windows)
Overzicht van scenario's
In dit scenario maakt u een apparaat dat de volgende telemetrie verzendt naar de vooraf geconfigureerde oplossing voor externe controle:
- Externe temperatuur
- Interne temperatuur
- Vochtigheid
Om het eenvoudig te houden, genereert de code op het apparaat voorbeeldwaarden, maar we moedigen u aan om het voorbeeld uit te breiden door echte sensoren met het apparaat te verbinden en echte telemetrie te verzenden.
Het apparaat kan ook reageren op methoden die zijn aangeroepen vanuit het oplossingsdashboard en op waarden van gewenste eigenschappen die in het oplossingsdashboard zijn ingesteld.
U hebt een actief Azure-account nodig om deze zelfstudie te voltooien. Als u geen account hebt, kunt u binnen een paar minuten een gratis proefaccount maken. Zie Gratis proefversie van Azure voor meer informatie.
Voordat u begint
Voordat u code voor het apparaat gaat schrijven, moet u de vooraf geconfigureerde oplossing voor externe controle inrichten en een nieuw aangepast apparaat in die oplossing inrichten.
De vooraf geconfigureerde oplossing voor externe controle inrichten
Het apparaat dat u in deze zelfstudie maakt, verzendt gegevens naar een exemplaar van de vooraf geconfigureerde oplossing voor externe controle. Als u de vooraf geconfigureerde oplossing voor externe controle in uw Azure-account nog niet hebt ingericht, voer dan de volgende stappen uit:
- Klik op + de https://www.azureiotsolutions.com/ pagina om een oplossing te maken.
- Klik in het deelvenster Externe controle op Selecteren om de oplossing te maken.
- Voer op de pagina Externe bewakingsoplossing een zelfgekozen Oplossingsnaam in, selecteer de Regio waarin u deze wilt implementeren en selecteer het Azure-abonnement dat u wilt gebruiken. Klik vervolgens op Oplossing maken.
- Wacht tot het inrichtingsproces is voltooid.
Waarschuwing
De vooraf geconfigureerde oplossingen maken gebruik van factureerbare Azure-services. Zorg dat u de vooraf geconfigureerde oplossing uit uw abonnement verwijdert wanneer u klaar bent, om overbodige kosten te voorkomen. U kunt een vooraf geconfigureerde oplossing volledig uit uw abonnement verwijderen door naar de https://www.azureiotsolutions.com/ pagina te gaan.
Wanneer het inrichtingsproces voor de externe bewakingsoplossing is voltooid, klikt u op Starten om het dashboard van de oplossing in uw browser te openen.
Het apparaat inrichten in de externe bewakingsoplossing
Notitie
Als u al een apparaat in uw oplossing hebt ingericht, kunt u deze stap overslaan. U moet de referenties van het apparaat weten wanneer u de clienttoepassing maakt.
Een apparaat kan alleen verbinding maken met de vooraf geconfigureerde oplossing als het zichzelf met geldige referenties kan identificeren bij IoT Hub. U kunt de apparaatreferenties ophalen via het dashboard van de oplossing. Verderop in deze zelfstudie neemt u de referenties van het apparaat op in de clienttoepassing.
Als u een apparaat aan de externe bewakingsoplossing wilt toevoegen, voert u de volgende stappen uit in het dashboard van de oplossing:
Klik in de linkerbenedenhoek van het dashboard op Een apparaat toevoegen.
Klik in het deelvenster Aangepast apparaat op Nieuw toevoegen.
Kies Laat mij mijn eigen apparaat-id definiëren. Voer een apparaat-id in, bijvoorbeeld mijnapparaat, en klik op Id controleren om te controleren of de naam nog niet wordt gebruikt. Klik tot slot op Maken om het apparaat in te richten.
Noteer de referenties van het apparaat (apparaat-id, hostnaam van IoT Hub en apparaatsleutel). De clienttoepassing heeft deze waarden nodig om verbinding te maken met de externe bewakingsoplossing. Klik vervolgens op Gereed.
Selecteer uw apparaat in de lijst met apparaten in het oplossingsdashboard. Klik vervolgens in het deelvenster Apparaatdetails op Apparaat inschakelen. De status van het apparaat is nu Wordt uitgevoerd. De externe bewakingsoplossing kan nu telemetrie ontvangen van uw apparaat en methoden op het apparaat aanroepen.
Een C-voorbeeldoplossing maken in Windows
In de volgende stappen ziet u hoe u een clienttoepassing maakt die communiceert met de vooraf geconfigureerde oplossing voor externe bewaking. Deze toepassing is geschreven in C en gebouwd en uitgevoerd in Windows.
Maak een startersproject in Visual Studio 2015 of Visual Studio 2017 en voeg de NuGet-pakketten van de IoT Hub-apparaatclient toe:
Maak in Visual Studio een C-consoletoepassing met behulp van de Visual C++ Win32-consoletoepassingssjabloon . Geef het project de naam RMDevice.
Controleer op de pagina Toepassingsinstellingen in de wizard Win32-toepassing of consoletoepassing is geselecteerd en schakel vooraf gecompileerde header - en SDL-controles (Security Development Lifecycle) uit.
Verwijder in Solution Explorer de bestanden stdafx.h, targetver.h en stdafx.cpp.
Wijzig in Solution Explorer de naam van het bestand RMDevice.cpp in RMDevice.c.
Klik in Solution Explorer met de rechtermuisknop op het RMDevice-project en klik vervolgens op NuGet-pakketten beheren. Klik op Bladeren en zoek en installeer de volgende NuGet-pakketten:
- Microsoft.Azure.IoTHub.Serializer
- Microsoft.Azure.IoTHub.IoTHubClient
- Microsoft.Azure.IoTHub.MqttTransport
Klik in Solution Explorer met de rechtermuisknop op het RMDevice-project en klik vervolgens op Eigenschappen om het dialoogvenster Eigenschappenpagina's van het project te openen. Zie Eigenschappen van Visual C++-project instellen voor meer informatie.
Klik op de map Linker en klik vervolgens op de pagina Invoereigenschap .
Voeg crypt32.lib toe aan de eigenschap Aanvullende afhankelijkheden . Klik op OK en vervolgens nogmaals op OK om de waarden van de projecteigenschap op te slaan.
Voeg de Parson JSON-bibliotheek toe aan het RMDevice-project en voeg de vereiste #include
instructies toe:
Kloon in een geschikte map op uw computer de Parson GitHub-opslagplaats met behulp van de volgende opdracht:
git clone https://github.com/kgabis/parson.git
Kopieer de parson.h- en parson.c-bestanden van de lokale kopie van de Parson-opslagplaats naar uw RMDevice-projectmap .
Klik in Visual Studio met de rechtermuisknop op het RMDevice-project , klik op Toevoegen en klik vervolgens op Bestaand item.
Selecteer in het dialoogvenster Bestaand item toevoegen de bestanden parson.h en parson.c in de projectmap RMDevice . Klik vervolgens op Toevoegen om deze twee bestanden toe te voegen aan uw project.
Open in Visual Studio het bestand RMDevice.c. Vervang de bestaande
#include
instructies door de volgende code:#include "iothubtransportmqtt.h" #include "schemalib.h" #include "iothub_client.h" #include "serializer_devicetwin.h" #include "schemaserializer.h" #include "azure_c_shared_utility/threadapi.h" #include "azure_c_shared_utility/platform.h" #include "parson.h"
Notitie
U kunt nu controleren of uw project de juiste afhankelijkheden heeft ingesteld door het te bouwen.
Het gedrag van het IoT-apparaat opgeven
De clientbibliotheek van de IoT Hub-serialisatiefunctie maakt gebruik van een model om de opmaak op te geven van de berichten die het apparaat uitwisselt met IoT Hub.
Voeg de volgende variabelendeclaraties achter de
#include
-instructies toe. Vervang de tijdelijke aanduidingen [Apparaat-id] en [Apparaatsleutel] door waarden die u voor uw apparaat hebt genoteerd in het dashboard van de externe bewakingsoplossing. Gebruik de hostnaam van de IoT Hub uit het oplossingsdashboard om [IoTHub-naam] te vervangen. Als uw IoT Hub-hostnaam bijvoorbeeld contoso.azure devices.net is, vervangt u [IoTHub-naam] door contoso:static const char* deviceId = "[Device Id]"; static const char* connectionString = "HostName=[IoTHub Name].azure-devices.net;DeviceId=[Device Id];SharedAccessKey=[Device Key]";
Voeg de volgende code toe om het model te definiëren dat het apparaat in staat stelt om met IoT Hub te communiceren. Dit model bepaalt dat het apparaat:
- Kan temperatuur, externe temperatuur, vochtigheid en een apparaat-id als telemetrie verzenden.
- Metagegevens over het apparaat naar IoT Hub kan verzenden. Het apparaat verzendt bij het opstarten basismetagegevens in een DeviceInfo-object.
- Gerapporteerde eigenschappen naar de apparaatdubbel in IoT Hub kan verzenden. Deze gerapporteerde eigenschappen zijn gegroepeerd in configuratie-, apparaat- en systeemeigenschappen.
- Gewenste eigenschappen die in de apparaatdubbel in IoT Hub zijn ingesteld, kan ontvangen en hierop kan reageren.
- Kan reageren op de directe methoden Reboot en InitiateFirmwareUpdate die via de oplossingsportal worden aangeroepen. Met behulp van gerapporteerde eigenschappen stuurt het apparaat informatie over de ondersteunde directe methoden.
// Define the Model BEGIN_NAMESPACE(Contoso); /* Reported properties */ DECLARE_STRUCT(SystemProperties, ascii_char_ptr, Manufacturer, ascii_char_ptr, FirmwareVersion, ascii_char_ptr, InstalledRAM, ascii_char_ptr, ModelNumber, ascii_char_ptr, Platform, ascii_char_ptr, Processor, ascii_char_ptr, SerialNumber ); DECLARE_STRUCT(LocationProperties, double, Latitude, double, Longitude ); DECLARE_STRUCT(ReportedDeviceProperties, ascii_char_ptr, DeviceState, LocationProperties, Location ); DECLARE_MODEL(ConfigProperties, WITH_REPORTED_PROPERTY(double, TemperatureMeanValue), WITH_REPORTED_PROPERTY(uint8_t, TelemetryInterval) ); /* Part of DeviceInfo */ DECLARE_STRUCT(DeviceProperties, ascii_char_ptr, DeviceID, _Bool, HubEnabledState ); DECLARE_DEVICETWIN_MODEL(Thermostat, /* Telemetry (temperature, external temperature and humidity) */ WITH_DATA(double, Temperature), WITH_DATA(double, ExternalTemperature), WITH_DATA(double, Humidity), WITH_DATA(ascii_char_ptr, DeviceId), /* DeviceInfo */ WITH_DATA(ascii_char_ptr, ObjectType), WITH_DATA(_Bool, IsSimulatedDevice), WITH_DATA(ascii_char_ptr, Version), WITH_DATA(DeviceProperties, DeviceProperties), /* Device twin properties */ WITH_REPORTED_PROPERTY(ReportedDeviceProperties, Device), WITH_REPORTED_PROPERTY(ConfigProperties, Config), WITH_REPORTED_PROPERTY(SystemProperties, System), WITH_DESIRED_PROPERTY(double, TemperatureMeanValue, onDesiredTemperatureMeanValue), WITH_DESIRED_PROPERTY(uint8_t, TelemetryInterval, onDesiredTelemetryInterval), /* Direct methods implemented by the device */ WITH_METHOD(Reboot), WITH_METHOD(InitiateFirmwareUpdate, ascii_char_ptr, FwPackageURI), /* Register direct methods with solution portal */ WITH_REPORTED_PROPERTY(ascii_char_ptr_no_quotes, SupportedMethods) ); END_NAMESPACE(Contoso);
Het gedrag van het apparaat implementeren
Voeg nu code toe om het gedrag te implementeren dat in het model is gedefinieerd.
Voeg de volgende functies toe die de gewenste eigenschappen verwerken die in het oplossingsdashboard zijn ingesteld. De volgende gewenste eigenschappen zijn in het model gedefinieerd:
void onDesiredTemperatureMeanValue(void* argument) { /* By convention 'argument' is of the type of the MODEL */ Thermostat* thermostat = argument; printf("Received a new desired_TemperatureMeanValue = %f\r\n", thermostat->TemperatureMeanValue); } void onDesiredTelemetryInterval(void* argument) { /* By convention 'argument' is of the type of the MODEL */ Thermostat* thermostat = argument; printf("Received a new desired_TelemetryInterval = %d\r\n", thermostat->TelemetryInterval); }
Voeg de volgende functies toe die de directe methoden verwerken die via de IoT Hub worden aangeroepen. De volgende directe methoden zijn in het model gedefinieerd:
/* Handlers for direct methods */ METHODRETURN_HANDLE Reboot(Thermostat* thermostat) { (void)(thermostat); METHODRETURN_HANDLE result = MethodReturn_Create(201, "\"Rebooting\""); printf("Received reboot request\r\n"); return result; } METHODRETURN_HANDLE InitiateFirmwareUpdate(Thermostat* thermostat, ascii_char_ptr FwPackageURI) { (void)(thermostat); METHODRETURN_HANDLE result = MethodReturn_Create(201, "\"Initiating Firmware Update\""); printf("Recieved firmware update request. Use package at: %s\r\n", FwPackageURI); return result; }
Voeg de volgende functie toe die een bericht naar de vooraf geconfigureerde oplossing verzendt:
/* Send data to IoT Hub */ static void sendMessage(IOTHUB_CLIENT_HANDLE iotHubClientHandle, const unsigned char* buffer, size_t size) { IOTHUB_MESSAGE_HANDLE messageHandle = IoTHubMessage_CreateFromByteArray(buffer, size); if (messageHandle == NULL) { printf("unable to create a new IoTHubMessage\r\n"); } else { if (IoTHubClient_SendEventAsync(iotHubClientHandle, messageHandle, NULL, NULL) != IOTHUB_CLIENT_OK) { printf("failed to hand over the message to IoTHubClient"); } else { printf("IoTHubClient accepted the message for delivery\r\n"); } IoTHubMessage_Destroy(messageHandle); } free((void*)buffer); }
Voeg de volgende callbackhandler toe die wordt uitgevoerd wanneer het apparaat nieuwe gerapporteerde eigenschapswaarden naar de vooraf geconfigureerde oplossing heeft verzonden:
/* Callback after sending reported properties */ void deviceTwinCallback(int status_code, void* userContextCallback) { (void)(userContextCallback); printf("IoTHub: reported properties delivered with status_code = %u\n", status_code); }
Voeg de volgende functie toe om het apparaat te verbinden met de vooraf geconfigureerde oplossing in de cloud, en gegevens uit te wisselen. Deze functie voert de volgende stappen uit:
- Initialiseert het platform.
- Registreert de Contoso-naamruimte bij de serialisatiebibliotheek.
- Initialiseert de client met de verbindingsreeks van het apparaat.
- Maakt een exemplaar van het thermostaatmodel.
- Maakt en verzendt gerapporteerde eigenschapswaarden.
- Verzendt een DeviceInfo-object.
- Maakt een lus om elke seconde telemetrie te verzenden.
- Deïnitialiseert alle resources.
void remote_monitoring_run(void) { if (platform_init() != 0) { printf("Failed to initialize the platform.\n"); } else { if (SERIALIZER_REGISTER_NAMESPACE(Contoso) == NULL) { printf("Unable to SERIALIZER_REGISTER_NAMESPACE\n"); } else { IOTHUB_CLIENT_HANDLE iotHubClientHandle = IoTHubClient_CreateFromConnectionString(connectionString, MQTT_Protocol); if (iotHubClientHandle == NULL) { printf("Failure in IoTHubClient_CreateFromConnectionString\n"); } else { #ifdef MBED_BUILD_TIMESTAMP // For mbed add the certificate information if (IoTHubClient_SetOption(iotHubClientHandle, "TrustedCerts", certificates) != IOTHUB_CLIENT_OK) { printf("Failed to set option \"TrustedCerts\"\n"); } #endif // MBED_BUILD_TIMESTAMP Thermostat* thermostat = IoTHubDeviceTwin_CreateThermostat(iotHubClientHandle); if (thermostat == NULL) { printf("Failure in IoTHubDeviceTwin_CreateThermostat\n"); } else { /* Set values for reported properties */ thermostat->Config.TemperatureMeanValue = 55.5; thermostat->Config.TelemetryInterval = 3; thermostat->Device.DeviceState = "normal"; thermostat->Device.Location.Latitude = 47.642877; thermostat->Device.Location.Longitude = -122.125497; thermostat->System.Manufacturer = "Contoso Inc."; thermostat->System.FirmwareVersion = "2.22"; thermostat->System.InstalledRAM = "8 MB"; thermostat->System.ModelNumber = "DB-14"; thermostat->System.Platform = "Plat 9.75"; thermostat->System.Processor = "i3-7"; thermostat->System.SerialNumber = "SER21"; /* Specify the signatures of the supported direct methods */ thermostat->SupportedMethods = "{\"Reboot\": \"Reboot the device\", \"InitiateFirmwareUpdate--FwPackageURI-string\": \"Updates device Firmware. Use parameter FwPackageURI to specify the URI of the firmware file\"}"; /* Send reported properties to IoT Hub */ if (IoTHubDeviceTwin_SendReportedStateThermostat(thermostat, deviceTwinCallback, NULL) != IOTHUB_CLIENT_OK) { printf("Failed sending serialized reported state\n"); } else { printf("Send DeviceInfo object to IoT Hub at startup\n"); thermostat->ObjectType = "DeviceInfo"; thermostat->IsSimulatedDevice = 0; thermostat->Version = "1.0"; thermostat->DeviceProperties.HubEnabledState = 1; thermostat->DeviceProperties.DeviceID = (char*)deviceId; unsigned char* buffer; size_t bufferSize; if (SERIALIZE(&buffer, &bufferSize, thermostat->ObjectType, thermostat->Version, thermostat->IsSimulatedDevice, thermostat->DeviceProperties) != CODEFIRST_OK) { (void)printf("Failed serializing DeviceInfo\n"); } else { sendMessage(iotHubClientHandle, buffer, bufferSize); } /* Send telemetry */ thermostat->Temperature = 50; thermostat->ExternalTemperature = 55; thermostat->Humidity = 50; thermostat->DeviceId = (char*)deviceId; while (1) { unsigned char*buffer; size_t bufferSize; (void)printf("Sending sensor value Temperature = %f, Humidity = %f\n", thermostat->Temperature, thermostat->Humidity); if (SERIALIZE(&buffer, &bufferSize, thermostat->DeviceId, thermostat->Temperature, thermostat->Humidity, thermostat->ExternalTemperature) != CODEFIRST_OK) { (void)printf("Failed sending sensor value\r\n"); } else { sendMessage(iotHubClientHandle, buffer, bufferSize); } ThreadAPI_Sleep(1000); } IoTHubDeviceTwin_DestroyThermostat(thermostat); } } IoTHubClient_Destroy(iotHubClientHandle); } serializer_deinit(); } } platform_deinit(); }
Ter referentie volgt hier een voorbeeld van een telemetriebericht dat naar de vooraf geconfigureerde oplossing is verzonden:
{"DeviceId":"mydevice01", "Temperature":50, "Humidity":50, "ExternalTemperature":55}
Het voorbeeldproject compileren en uitvoeren
Voeg code toe om de remote_monitoring_run-functie aan te roepen en vervolgens de apparaattoepassing te bouwen en uit te voeren.
Vervang de hoofdfunctie door de volgende code om de functie remote_monitoring_run aan te roepen:
int main() { remote_monitoring_run(); return 0; }
Klik op Build en vervolgens Build Solution om de apparaattoepassing te bouwen.
Klik in Solution Explorer met de rechtermuisknop op het RMDevice-project, klik op Fouten opsporen en klik vervolgens op Nieuw exemplaar starten om het voorbeeld uit te voeren. De console geeft berichten weer wanneer de toepassing voorbeeldtelemetrie verzendt naar de vooraf geconfigureerde oplossing, ontvangt de gewenste eigenschapswaarden die zijn ingesteld in het oplossingsdashboard en reageert op methoden die worden aangeroepen vanuit het oplossingsdashboard.
Telemetrie van apparaten weergeven in het dashboard
Via het dashboard van de externe bewakingsoplossing kunt u de telemetrie bekijken die uw apparaten naar IoT Hub verzenden.
Ga in de browser terug naar het dashboard van de externe bewakingsoplossing en klik in het linkerdeelvenster op Apparaten om naar de Lijst met apparaten te navigeren.
In de Lijst met apparaten zou de status van uw apparaat nu Wordt uitgevoerd moeten zijn. Als dat niet zo is, klikt u in het deelvenster Apparaatdetails op Apparaat inschakelen.
Klik op Dashboard om terug te keren naar het dashboard en selecteer het apparaat in de vervolgkeuzelijst Weer te geven apparaat om de telemetrie ervan weer te geven. De telemetrie uit de voorbeeldtoepassing is 50 eenheden voor de interne temperatuur, 55 eenheden voor de externe temperatuur en 50 eenheden voor de vochtigheid.
Een methode op het apparaat aanroepen
Via het dashboard van de externe bewakingsoplossing kunt u methoden op uw apparaten aanroepen via IoT Hub. U kunt in de externe bewakingsoplossing bijvoorbeeld een methode aanroepen om het opnieuw opstarten van een apparaat te simuleren.
Klik op het dashboard van de externe bewakingsoplossing in het linkerdeelvenster op Apparaten om naar de Lijst met apparaten te navigeren.
Klik in de Lijst met apparaten op Apparaat-id voor uw apparaat.
Klik in het deelvenster Apparaatdetails op Methoden.
Selecteer in de vervolgkeuzelijst Methode de methode InitiateFirmwareUpdate en voer in FWPACKAGEURI een dummy URL in. Klik op Methode aanroepen om de methode op het apparaat aan te roepen.
In de console waarin de apparaatcode wordt uitgevoerd, wordt een bericht weergegeven wanneer het apparaat de methode afhandelt. De resultaten van de methode worden toegevoegd aan de geschiedenis in de portal van de oplossing:
Volgende stappen
In het artikel Customizing preconfigured solutions (Vooraf geconfigureerde oplossingen aanpassen) worden enkele manieren beschreven waarop u dit voorbeeld kunt uitbreiden. Mogelijke uitbreidingen zijn het gebruik van echte sensoren en de implementatie van aanvullende opdrachten.
Zie Permissions on the azureiotsuite.com site (Machtigingen op de site azureiotsuite.com) voor meer informatie.