Отправка сообщения Cloud-to-Device на устройства, предоставляемые через IoT-central - PullRequest
0 голосов
/ 14 декабря 2018

Я читал документацию этого нового предложения SaaS, но я не вижу никаких упоминаний о возможности отправки сообщения на устройство, например: включить / выключить оборудование .

https://docs.microsoft.com/en-us/azure/iot-central/tutorial-add-device

Я вижу, что есть возможность изменить настройки устройства, так как можно изменить устройство-близнец.Также я читал, что есть способ отправить «эхо» на устройство.Но они не служат моей точной цели.

Итак, есть ли способ, которым я могу отправить сообщение C2D, используя строку подключения, которая может быть построена с помощью процедуры-?https://docs.microsoft.com/en-us/azure/iot-central/tutorial-add-device#prepare-the-client-code

Я хотел бы отправить этот C2D через AzureFunction, но было бы полезно узнать, можно ли его каким-либо образом интегрировать в интерфейс IoT-Central.

Любые другие входы дляВыполнить мое требование ( включить / выключить оборудование ) также было бы очень полезно!

Спасибо и всего наилучшего,

Ответы [ 3 ]

0 голосов
/ 31 декабря 2018

Как я уже упоминал в своем комментарии, Azure IoT Central полностью контролирует внутреннюю конечную точку, ориентированную на службу IoT Hub.Однако есть способ, при котором Azure IoT Central разрешает ограниченный доступ к этой конечной точке, ориентированной на службы, и использует REST API для обработки двойника устройства и вызова прямого метода на устройстве.

Ниже приведеныПорядок получения токена sas для заголовка авторизации, необходимого для вызовов API REST:

  1. Получите токен доступа из приложения Azure IoT Central.

    формат:

    SharedAccessSignature sr=appId&sig=xxxxx&skn=myTokenName&se=1577730019340
    

    Обратите внимание, что appId показывает идентификатор приложения вашего приложения Azure IoT Central

  2. Вызовите запрос REST POST, чтобы получить iothubTenantSasToken.sasToken

    POST https://api.azureiotcentral.com/v1-beta/applications/{appId}/diagnostics/sasTokens  
    Authorization:SharedAccessSignature sr=appId&sig=xxxxx&skn=myTokenName&se=1577730019340
    

    Ответ имеет следующий формат:

    {
      "iothubTenantSasToken": {
        "sasToken": "SharedAccessSignature sr=saas-iothub-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx.azure-devices.net&sig=xxxxx&se=1546197703&skn=service"
        },
      "eventhubSasToken": {
        "sasToken": "SharedAccessSignature sr=sb%3A%2F%2Fep-ns-saas-ep-15-262-xxxxxxxxxx.servicebus.windows.net%2Fep-ehub-saas-iothu-1044564-xxxxxxxxxx&sig=xxxxxx&se=1546197703&skn=service",
        "entityPath": "ep-ehub-saas-iothu-1044564-xxxxxxxxxx",
        "hostname": "sb://ep-ns-saas-ep-15-262-xxxxxxxxxx.servicebus.windows.net/"
        },
      "expiry": 1546197703
    }
    
  3. SasToken для наших обращающихся к сервису вызовов конечных точек:

    SharedAccessSignature sr=saas-iothub-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx.azure-devices.net&sig=xxxxx&se=1546197703&skn=service
    

Теперь мы можем использовать некоторые API-интерфейсы REST Azure IoT Hub, в основном вызовы с twins в пути uri, например:

https://docs.microsoft.com/en-us/rest/api/iothub/service/gettwin

https://docs.microsoft.com/en-us/rest/api/iothub/service/updatetwin

https://docs.microsoft.com/en-us/rest/api/iothub/service/replacetwin

https://docs.microsoft.com/en-us/rest/api/iothub/service/invokedevicemethod

Пример вызова метода Direct на устройстве1:

POST https://saas-iothub-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx.azure-devices.net/twins/device1/methods?api-version=2018-06-30
Authorization:SharedAccessSignature sr=saas-iothub-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx.azure-devices.net&sig=xxxxx&se=1546197703&skn=service

body:
    {
      "methodName": "writeLine",
      "timeoutInSeconds": 20,
      "payload": {
         "input1": 12345,
         "input2": "HelloDevice"
         }
    }

Пример обновления свойства двойных тегов устройства:

PATCH https://saas-iothub-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx.azure-devices.net/twins/device1?api-version=2018-06-30
Authorization:SharedAccessSignature sr=saas-iothub-xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx.azure-devices.net&sig=xxxxx&se=1546197703&skn=service

body:
    {
      "tags": {
        "test":12345
        }
    }

Обратите внимание, что срок действия sasToken expiry время 60 минут.Я рекомендую кешировать объект ответа с шага 2. и обновлять в зависимости от времени истечения.

ОБНОВЛЕНИЕ:

Ниже приведены шаги по использованию токена доступа IoT Central для обработки двойников устройства и прямого метода устройства в функции azure.

Создание токена доступа в приложении IoT Central, см. Следующий фрагмент экрана:

enter image description here

Добавьте этот токен доступа к настройкам приложения-функции.В этом примере Имя параметра приложения используется AzureIoTCAccessToken .Обратите внимание, что этот токен доступа можно сохранить в хранилище ключей Azure, подробнее см. здесь .

Создать функцию HttpTrigger в вашем приложении функций.

Заменить run.csx следующим кодом:

#r "Newtonsoft.Json"
#r "Microsoft.Azure.WebJobs.Extensions.Http"

using System.Net;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Primitives;
using Microsoft.Azure.WebJobs.Extensions.Http;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using System.Linq;
using System.Text;

// reusable client proxy
static HttpClientHelper iothub = new HttpClientHelper(Environment.GetEnvironmentVariable("AzureIoTCAccessToken"));

public static async Task<IActionResult> Run(HttpRequest req, ILogger log)
{
    log.LogInformation("C# HTTP trigger function processed a request.");

    var atype = new { device = new { deviceId = "", properties = new JObject(), measurements = new JObject() } };
    var iotcobj = JsonConvert.DeserializeAnonymousType(await req.ReadAsStringAsync(), atype);

    // get deviceId, for test puspose use the device1
    string deviceId = iotcobj?.device?.deviceId ?? "device1";

    // get a device twins
    var response = await iothub.Client.GetAsync($"/twins/{deviceId}?api-version=2018-06-30");
    string jsontext = await response.Content.ReadAsStringAsync();
    log.LogInformation($"DeviceTwin: {JsonConvert.DeserializeObject(jsontext)}");

   // patch on desired property
   var patch = JsonConvert.SerializeObject(new { properties = new { desired = new { ping = DateTime.UtcNow } } });
   response = await iothub.Client.PatchAsync($"/twins/{deviceId}?api-version=2018-06-30", new StringContent(patch, Encoding.UTF8, "application/json"));
   jsontext = await response.Content.ReadAsStringAsync();
   log.LogInformation($"Patch: {JsonConvert.DeserializeObject(jsontext)}");

   // invoke a device method
   var method = new { methodName = "writeLine", timeoutInSeconds = 30, payload = new {input1 = 12345, input2 = "HelloDevice" } };
   response = await iothub.Client.PostAsJsonAsync($"/twins/{deviceId}/methods?api-version=2018-06-30", method );
   jsontext = await response.Content.ReadAsStringAsync();
   log.LogInformation($"DirectMethod: {JsonConvert.DeserializeObject(jsontext)}");

   return new OkObjectResult(jsontext);      
}

class HttpClientHelper
{
    HttpClient client;
    string accessToken;
    dynamic iothub;
    long toleranceInSeconds = 60;

    public HttpClientHelper(string accessToken)
    {
        this.accessToken = accessToken;
        this.iothub = GetIoTHubTenant(accessToken);
        string hostname = GetHostNameFromSaSToken(this.iothub.iothubTenantSasToken.sasToken);
        client = new HttpClient() { BaseAddress = new Uri($"https://{hostname}") };
        client.DefaultRequestHeaders.Add("Authorization", iothub.iothubTenantSasToken.sasToken);
    }
    public HttpClient Client
    {
        get
        {
            if((new DateTime(1970, 1, 1)).AddSeconds(this.iothub.expiry - toleranceInSeconds) < DateTime.UtcNow)
                SetAuthorizationHeader();
            return client;
        }
    }
    private void SetAuthorizationHeader()
    {
        lock (client)
        {
            if ((new DateTime(1970, 1, 1)).AddSeconds(this.iothub.expiry - toleranceInSeconds) < DateTime.UtcNow)
            {
                if (client.DefaultRequestHeaders.Contains("Authorization"))
                    client.DefaultRequestHeaders.Remove("Authorization");
                this.iothub = GetIoTHubTenant(this.accessToken);
                client.DefaultRequestHeaders.Add("Authorization", this.iothub.iothubTenantSasToken.sasToken);
            }
        }
    }
    private string GetHostNameFromSaSToken(string sastoken)
    {
        var parts = sastoken.Replace("SharedAccessSignature", "").Split(new[] { '&' }, StringSplitOptions.RemoveEmptyEntries).Select(s => s.Split(new[] { '=' }, 2)).ToDictionary(x => x[0].Trim(), x => x[1].Trim());
        return parts["sr"] ?? "";
    }

    private dynamic GetIoTHubTenant(string iotcAccessToken)
    {
        string appId = GetHostNameFromSaSToken(iotcAccessToken);
        using (var hc = new HttpClient())
        {
            hc.DefaultRequestHeaders.Add("Authorization", accessToken);
            string address = $"https://api.azureiotcentral.com/v1-beta/applications/{appId}/diagnostics/sasTokens";
            var response = hc.PostAsync(address, new StringContent("{}", Encoding.UTF8, "application/json")).Result;
            return JsonConvert.DeserializeAnonymousType(response.Content.ReadAsStringAsync().Result, new { iothubTenantSasToken = new { sasToken = "" }, expiry = 0L });
        }
    }
}

Примечание: , вышеприведенная реализация основана на сгенерированном токене доступа вашего приложения IoT Central, как будто он недавно был выпущен для всеобщей доступности, см. здесь .В случае изменения формата и т. Д. Все клиенты, тестировщики и т. Д., Включенные в вышеуказанное решение, будут затронуты.

0 голосов
/ 04 января 2019

Для вашего конкретного случая использования сегодня единственный способ сделать это - запустить рабочий процесс приложения логики, используя его конечную точку HTTP из функций Azure.В приложении логики вы можете создать рабочий процесс с помощью Azure IoT Central коннектора , который обновляет свойства и настройки устройства.

Мы работаем над API-интерфейсами в IoT Central, которые могут освещать такие случаи использования, какваш, так что следите за обновлениями!

0 голосов
/ 26 декабря 2018

Вы можете попробовать использовать Настройки , существует тип настройки, называемый «Переключить».Чтобы реализовать это, вы можете зайти в центральное приложение IoT с портала Azure.Затем:

  • Перейдите на вкладку «Обозреватель устройств»

  • Выберите устройство

  • Нажмите на вкладку «Настройки»для устройства
  • Нажмите кнопку «Редактировать шаблон», расположенную в верхнем правом углу
  • В разделе «Библиотека» найдите и нажмите «Переключить»

enter image description here

  • Введите настройки для функции переключения

enter image description here

Если вы хотите сделать это в масштабе , вы можете Создать и запустить задание

В IoT Central вы можете управлять подключенными устройствами в масштабе с помощью заданий.Функциональные возможности заданий позволяют выполнять массовые обновления свойств, настроек и команд устройства.

...