【问题标题】:Azure App Service can not get data from Azure IoT HubAzure 应用服务无法从 Azure IoT 中心获取数据
【发布时间】:2018-06-26 11:31:26
【问题描述】:

我想使用 Azure App Service 从 Azure IoT Hub 获取数据。

我尝试在 Application_Start() 函数中向 IoT Hub 注册回调事件。

当我可以在我的 PC 上使用 Visual Studio 2017 运行我的程序时,Azure IoT Hub 会正常触发事件并获取数据。

不幸的是,当我部署到服务“Azure App Service”的Azure云时,它只能在应用服务启动几秒钟后从Azure IoT Hub获取触发事件。

没有从 Azure IoT 中心返回数据,事件不再触发。

我不知道原因。任何建议都会被采纳。

这里是事件触发代码将在应用服务的初始运行。 入口点是 Main() 函数。



    using Microsoft.ServiceBus.Messaging;
    using System;
    using System.Collections.Generic;
    using System.Configuration;
    using System.Linq;
    using System.Threading.Tasks;
    using System.Web;
    using TelemetryEPHostConsoleApp;

    namespace MCM100_Dashboard.App_Start.TelemetryProcessor
    {
        public class TelemetryMain
        {
            private const string STORAGEACCOUNT_PROTOCOL = "https";// We use HTTPS to access the storage account

            public async static void Main()
            {
                var mainTask = new Task(GetAzureData);
                mainTask.Start();
                await mainTask;
            }
            public static string GetAzureData()
            {
               // IoT Hub
                string iotHubConnectionString = ConfigurationManager.AppSettings["IoTHub.ConnectionString"];
                string eventHubPath = "messages/events";// It's hard-coded for IoT Hub
                string consumerGroupName = "mcmpush";// It's hard-coded for this workshop

                // Storage Account
                string storageAccountName = ConfigurationManager.AppSettings["StorageAccount.Name"];
                string storageAccountKey = ConfigurationManager.AppSettings["StorageAccount.Key"];
                string storageAccountConnectionString = CombineConnectionString(storageAccountName, storageAccountKey);
                string eventProcessorHostName = "eventprocessorhost";
                string leaseName = eventProcessorHostName;

                EventProcessorHost eventProcessorHost = new EventProcessorHost(
                    eventProcessorHostName,
                    eventHubPath,
                    consumerGroupName,
                    iotHubConnectionString,
                    storageAccountConnectionString,
                    leaseName);


                var options = new EventProcessorOptions
                {
                    InitialOffsetProvider = (partitionId) => DateTime.UtcNow
                };
                options.ExceptionReceived += (sender, e) => { Console.WriteLine(e.Exception); };
                re: try
                {
                    eventProcessorHost.RegisterEventProcessorAsync(options).Wait();
                }
                catch (Exception e)
                {
                    System.Threading.Thread.Sleep(1000);
                    goto re;
                }


                eventProcessorHost.UnregisterEventProcessorAsync().Wait();

                return "";

            }

            private static string CombineConnectionString(string storageAccountName, string storageAccountKey)
            {
                return "DefaultEndpointsProtocol=" + STORAGEACCOUNT_PROTOCOL + ";" +
                    "AccountName=" + storageAccountName + ";" +
                    "AccountKey=" + storageAccountKey;
            }
        }
    }



    using Microsoft.ServiceBus.Messaging;
    using System;
    using System.Collections.Generic;
    using System.Diagnostics;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    using System.Net;
    using System.Configuration;
    using System.IO;
    using System.Web;

    namespace TelemetryEPHostConsoleApp
    {
        class TelemetryEventProcessor :IEventProcessor
        {
            static WebServerConnector _webSC = new WebServerConnector();

            async Task IEventProcessor.CloseAsync(PartitionContext context, CloseReason reason)
            {
                if (reason == CloseReason.Shutdown)
                {
                    await context.CheckpointAsync();
                }
            }

            Task IEventProcessor.OpenAsync(PartitionContext context)
            {
                return Task.FromResult(null);
            }

            async Task IEventProcessor.ProcessEventsAsync(PartitionContext context, IEnumerable messages)
            {
                // hope to trigger event
                foreach (EventData eventData in messages)
                {
                    string data = Encoding.UTF8.GetString(eventData.GetBytes());

                }

                //Call checkpoint every 5 minutes, so that worker can resume processing from 5 minutes back if it restarts.
                if (this.checkpointStopWatch.Elapsed > TimeSpan.FromMinutes(5))
                {
                    await context.CheckpointAsync();
                    this.checkpointStopWatch.Restart();
                }
            }

            private void ProcessMessage(string data)
            {
               return "";
            }

        }
    }

【问题讨论】:

  • 这方面有进展吗?
  • 好的,非常感谢。我们在其他服务中发现了另一个问题。损坏的问题是由于其他服务造成的,因此我无法识别该错误。非常感谢。
  • 解决此问题的方法是解决另一个将数据推送到 Azure IoTHub 的服务。我们发现它会在几分钟后断开连接。我在localhost中看到数据而在云端看不到数据的原因是“时间延迟”。当数据发送到 IoTHub 时,在 localhost 进行时间延迟,以便我可以在 Azure IoTHub 服务崩溃之前看到数据。另一方面,在 Azure IoTHub 服务崩溃后,云无法获取数据。由于这些原因,我们看到了这些情况。非常感谢。

标签: c# azure azure-web-app-service azure-iot-hub


【解决方案1】:

RegisterEventProcessorAsync 之后立即执行UnregisterEventProcessorAsync。这是为什么?您不允许有太多时间来处理事件。您最好使用持续运行的网络作业从 IoT 中心读取数据。

只有当您想停止监听传入事件时,您才应该调用UnregisterEventProcessorAsync。在您注册事件处理器之后和取消注册之前,运行时将调用 Task IEventProcessor.ProcessEventsAsync(PartitionContext context, IEnumerable messages) 任意次数。

另外,我看到几次 return ""; 是怎么回事?

【讨论】:

    猜你喜欢
    • 2019-01-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-11-11
    • 1970-01-01
    • 2022-01-11
    • 1970-01-01
    相关资源
    最近更新 更多