Beispiel #1
0
        private void InitializeClient()
        {
            // If the client reports Connected status, it is already in operational state.
            if (s_connectionStatus != ConnectionStatus.Connected &&
                _moduleConnectionStrings.Any())
            {
                lock (_initLock)
                {
                    _logger.LogDebug($"Attempting to initialize the client instance, current status={s_connectionStatus}");

                    // If the module client instance has been previously initialized, then dispose it.
                    // The s_wasEverConnected variable is required to store if the client ever reported Connected status.
                    if (s_wasEverConnected && s_connectionStatus == ConnectionStatus.Disconnected)
                    {
                        s_moduleClient?.Dispose();
                        s_wasEverConnected = false;
                    }

                    s_moduleClient = ModuleClient.CreateFromConnectionString(_moduleConnectionStrings.First(), _transportType);
                    s_moduleClient.SetConnectionStatusChangesHandler(ConnectionStatusChangeHandler);
                    s_moduleClient.OperationTimeoutInMilliseconds = (uint)s_operationTimeout.TotalMilliseconds;
                }

                try
                {
                    // Force connection now
                    s_moduleClient.OpenAsync().GetAwaiter().GetResult();
                    _logger.LogDebug($"Initialized the client instance.");
                }
                catch (UnauthorizedException)
                {
                    // Handled by the ConnectionStatusChangeHandler
                }
            }
        }
Beispiel #2
0
        private async Task ModuleClient_Gives_ConnectionStatus_DeviceDisabled_Base(
            Client.TransportType protocol, Func <RegistryManager, string, Task> registryManagerOperation)
        {
            AmqpTransportSettings amqpTransportSettings = new AmqpTransportSettings(protocol);

            ITransportSettings[] transportSettings = new ITransportSettings[] { amqpTransportSettings };

            TestModule testModule = await TestModule.GetTestModuleAsync(DevicePrefix + $"_{Guid.NewGuid()}", ModulePrefix).ConfigureAwait(false);

            ConnectionStatus?            status             = null;
            ConnectionStatusChangeReason?statusChangeReason = null;
            int deviceDisabledReceivedCount = 0;
            ConnectionStatusChangesHandler statusChangeHandler = (s, r) =>
            {
                if (r == ConnectionStatusChangeReason.Device_Disabled)
                {
                    status             = s;
                    statusChangeReason = r;
                    deviceDisabledReceivedCount++;
                }
            };

            using (ModuleClient moduleClient = ModuleClient.CreateFromConnectionString(testModule.ConnectionString, transportSettings))
            {
                moduleClient.SetConnectionStatusChangesHandler(statusChangeHandler);
                _log.WriteLine($"Created {nameof(DeviceClient)} ID={TestLogging.IdOf(moduleClient)}");

                Console.WriteLine("ModuleClient OpenAsync.");
                await moduleClient.OpenAsync().ConfigureAwait(false);

                // Receiving the module twin should succeed right now.
                Console.WriteLine("ModuleClient GetTwinAsync.");
                var twin = await moduleClient.GetTwinAsync().ConfigureAwait(false);

                Assert.IsNotNull(twin);

                // Delete/disable the device in IoT Hub.
                using (RegistryManager registryManager = RegistryManager.CreateFromConnectionString(Configuration.IoTHub.ConnectionString))
                {
                    await registryManagerOperation(registryManager, testModule.DeviceId).ConfigureAwait(false);
                }

                // Artificial sleep waiting for the connection status change handler to get triggered.
                int sleepCount = 50;
                for (int i = 0; i < sleepCount; i++)
                {
                    await Task.Delay(TimeSpan.FromSeconds(10)).ConfigureAwait(false);

                    if (deviceDisabledReceivedCount == 1)
                    {
                        break;
                    }
                }

                Assert.AreEqual(1, deviceDisabledReceivedCount);
                Assert.AreEqual(ConnectionStatus.Disconnected, status);
                Assert.AreEqual(ConnectionStatusChangeReason.Device_Disabled, statusChangeReason);
            }
        }
        public async Task InitiateSimulationAsync()
        {
            string logPrefix = "system".BuildLogPrefix();

            IoTTools.CheckModuleConnectionStringData(ModuleSettings.ConnectionString, _logger);

            // Connect to the IoT hub using the MQTT protocol

            _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::Module client created.");

            if (SimulationSettings.EnableTwinPropertiesDesiredChangesNotifications)
            {
                await _moduleClient.SetDesiredPropertyUpdateCallbackAsync(OnDesiredPropertyChange, null);

                _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::Twin Desired Properties update callback handler registered.");
            }

            //Configuration
            if (SimulationSettings.EnableC2DDirectMethods)
            {
                //Register C2D Direct methods handlers
                await RegisterC2DDirectMethodsHandlersAsync(_moduleClient, ModuleSettings, _logger);
            }

            if (SimulationSettings.EnableC2DMessages)
            {
                //Start receiving C2D messages

                ReceiveC2DMessagesAsync(_moduleClient, ModuleSettings, _logger);
            }

            //Messages
            if (SimulationSettings.EnableTelemetryMessages)
            {
                SendDeviceToCloudMessagesAsync(_moduleClient, ModuleSettings.DeviceId, ModuleSettings.ModuleId, _logger); //interval is a global variable changed by processes
            }
            if (SimulationSettings.EnableReadingTwinProperties)
            {
                //Twins
                _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::INITIALIZATION::Retrieving twin.");
                Twin twin = await _moduleClient.GetTwinAsync();

                if (twin != null)
                {
                    _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::INITIALIZATION::Device twin: {JsonConvert.SerializeObject(twin, Formatting.Indented)}.");
                }
                else
                {
                    _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::INITIALIZATION::No device twin.");
                }
            }

            _moduleClient.SetConnectionStatusChangesHandler(new ConnectionStatusChangesHandler(ConnectionStatusChanged));
        }
Beispiel #4
0
        /// <summary>
        /// Initializes the ModuleClient and sets up the callback to receive
        /// messages containing temperature information
        /// </summary>
        static async Task Init()
        {
            AmqpTransportSettings amqpSetting = new AmqpTransportSettings(TransportType.Amqp_Tcp_Only);

            ITransportSettings[] settings = { amqpSetting };

            Console.WriteLine("Open a connection to the Edge runtime");
            ioTHubModuleClient = await ModuleClient.CreateFromEnvironmentAsync(settings);

            ioTHubModuleClient.SetConnectionStatusChangesHandler(ConnectionStatusChanged);

            await ioTHubModuleClient.OpenAsync();

            Console.WriteLine("IoT Hub module client initialized.");
        }
Beispiel #5
0
        // Initialize the device client instance over Mqtt protocol (TCP, with fallback over Websocket), setting the ModelId into ClientOptions.
        // This method also sets a connection status change callback, that will get triggered any time the device's connection status changes.
        private static void InitializeDeviceClientAsync()
        {
            var options = new ClientOptions
            {
                ModelId = ModelId,
            };

            s_deviceClient = ModuleClient.CreateFromConnectionString(s_deviceConnectionString, TransportType.Mqtt, options);

            //s_deviceClient = DeviceClient.CreateFromConnectionString(s_deviceConnectionString, TransportType.Mqtt, options);
            s_deviceClient.SetConnectionStatusChangesHandler((status, reason) =>
            {
                s_logger.LogDebug($"Connection status change registered - status={status}, reason={reason}.");
            });
        }
Beispiel #6
0
        /// <summary>
        /// Initializes the ModuleClient and sets up the callback to receive
        /// messages containing temperature information
        /// </summary>
        static async Task Init()
        {
            MqttTransportSettings mqttSetting = new MqttTransportSettings(TransportType.Mqtt_Tcp_Only);

            ITransportSettings[] settings = { mqttSetting };

            // Open a connection to the Edge runtime

            moduleClient = ModuleClient.CreateFromConnectionString("");
            moduleClient.SetConnectionStatusChangesHandler(OnConnectionStatusChanged);
            await moduleClient.OpenAsync();

            Console.WriteLine("IoT Hub module client initialized.");

            timer = new Timer(new TimerCallback(Program.SendEvent), null, 5000 /*dueTime*/, 5000 /*period*/);
        }
Beispiel #7
0
        public DesiredPropertiesValidator(RegistryManager registryManager, ModuleClient moduleClient, TwinEventStorage storage, ITwinTestResultHandler resultHandler, TwinState twinState)
        {
            this.registryManager = registryManager;
            this.moduleClient    = moduleClient;
            this.storage         = storage;
            this.resultHandler   = resultHandler;
            this.twinState       = twinState;

            moduleClient.SetConnectionStatusChangesHandler((status, reason) =>
            {
                Logger.LogInformation($"Detected change in connection status:{Environment.NewLine}Changed Status: {status} Reason: {reason}");
                if (status == ConnectionStatus.Disconnected_Retrying)
                {
                    this.twinState.LastTimeOfEdgeRestart = DateTime.UtcNow;
                }
            });
        }
Beispiel #8
0
        /// <summary>
        /// Initializes the ModuleClient and sets up the callback to receive
        /// messages containing temperature information
        /// </summary>
        static async Task Init()
        {
            MqttTransportSettings mqttSetting = new MqttTransportSettings(TransportType.Mqtt_Tcp_Only);

            ITransportSettings[] settings = { mqttSetting };

            // Open a connection to the Edge runtime
            ModuleClient ioTHubModuleClient = await ModuleClient.CreateFromEnvironmentAsync(settings);

            await ioTHubModuleClient.OpenAsync();

            Console.WriteLine("IoT Hub module client initialized.");

            api = new InfsoftRest.InfsoftAPI();

            // Register callback to be called when a message is received by the module
            //await ioTHubModuleClient.SetInputMessageHandlerAsync("input1", PipeMessage, ioTHubModuleClient);

            ioTHubModuleClient.SetConnectionStatusChangesHandler(ConnectionStatusHandler);

            Guid apiKey    = Guid.Empty;
            var  apiKeyEnv = Environment.GetEnvironmentVariable("apikey");

            if (!string.IsNullOrEmpty(apiKeyEnv))
            {
                apiKey = Guid.Parse(apiKeyEnv);
            }

            int locationId    = 0;
            var locationIdEnv = Environment.GetEnvironmentVariable("locationid");

            if (!string.IsNullOrEmpty(locationIdEnv))
            {
                locationId = int.Parse(locationIdEnv);
            }

            int sleepDurationoInSec    = 0;
            var sleepDurationoInSecEnv = Environment.GetEnvironmentVariable("sleepdurationoinsec");

            if (!string.IsNullOrEmpty(sleepDurationoInSecEnv))
            {
                sleepDurationoInSec = int.Parse(sleepDurationoInSecEnv);
            }

            await SendInfsoftTrackingAssetTelemetry(ioTHubModuleClient, cts.Token, apiKey, locationId, sleepDurationoInSec);
        }
Beispiel #9
0
        public async Task Init(CancellationTokenSource cancellationTokenSource)
        {
            var tokenHelper = new SecurityDaemonClient();

            while (!cancellationTokenSource.IsCancellationRequested)
            {
                try
                {
                    Console.WriteLine($"tokenHelper: '{tokenHelper.ToString()}'");
                    var token = tokenHelper.GetModuleToken(3600).Result;
                    Console.WriteLine($"Token: '{token}'");
                    var tokenAuthentication = new ModuleAuthenticationWithToken(tokenHelper.DeviceId, tokenHelper.ModuleId, token);

                    var transportType             = new MqttTransportSettings(TransportType.Mqtt_Tcp_Only);
                    ITransportSettings[] settings = { transportType };
                    using (ModuleClient moduleClient = ModuleClient.Create(tokenHelper.IotHubHostName, tokenAuthentication, settings))
                    {
                        if (moduleClient == null)
                        {
                            Console.WriteLine("Failed to create ModuleClient!");
                            throw new InvalidOperationException("Failed to create ModuleClient");
                        }
                        moduleClient.SetConnectionStatusChangesHandler((ConnectionStatus status, ConnectionStatusChangeReason reason) =>
                        {
                            if (reason == ConnectionStatusChangeReason.Bad_Credential)
                            {
                                Init(cancellationTokenSource).Wait();
                            }
                        });

                        Console.WriteLine($"Starting DeviceStreamSample on '{_hostName}:{_port}'");
                        await RunSampleAsync(moduleClient, true, cancellationTokenSource);
                    }
                }
                catch (Exception ex)
                {
                    Console.WriteLine($"{DateTime.UtcNow} - Got an exception: {ex.ToString()}");
                    Console.WriteLine("Waiting 1 minute and trying again...");
                    await Task.Delay(TimeSpan.FromMinutes(1));
                }
            }
        }
        public async Task Initialize(ConnectionStatusChangesHandler connectionStatusHander, MessageHandler messageCallback, DesiredPropertyUpdateCallback twinCallback, MethodCallback methodCallback, object context, CancellationToken ct)
        {
            var option = new ClientOptions
            {
                ModelId = ModuleClientConnector.PnPModelId
            };

            moduleClient = await ModuleClient.CreateFromEnvironmentAsync(envSettings, options : option);

            Console.WriteLine($"Connected to Edge Hub as Plug and Play Model Id={ModuleClientConnector.PnPModelId}");

            await moduleClient.OpenAsync();

            moduleClient.SetConnectionStatusChangesHandler(connectionStatusHander);
            await moduleClient.SetInputMessageHandlerAsync(this.msgInputName, messageCallback, context);

            await moduleClient.SetDesiredPropertyUpdateCallbackAsync(twinCallback, context);

            await moduleClient.SetMethodDefaultHandlerAsync(methodCallback, context);
        }
Beispiel #11
0
        TwinAllOperationsInitializer(RegistryManager registryManager, ModuleClient moduleClient, ITwinTestResultHandler resultHandler, TwinEventStorage storage, TwinTestState twinTestState)
        {
            this.registryManager             = registryManager;
            this.twinTestState               = twinTestState;
            this.reportedPropertyUpdater     = new ReportedPropertyUpdater(moduleClient, resultHandler, twinTestState.ReportedPropertyUpdateCounter);
            this.desiredPropertyUpdater      = new DesiredPropertyUpdater(registryManager, resultHandler, twinTestState);
            this.desiredPropertyReceiver     = new DesiredPropertyReceiver(moduleClient, resultHandler);
            this.reportedPropertiesValidator = new ReportedPropertiesValidator(registryManager, moduleClient, storage, resultHandler, twinTestState);
            this.desiredPropertiesValidator  = new DesiredPropertiesValidator(registryManager, moduleClient, storage, resultHandler, twinTestState);

            moduleClient.SetConnectionStatusChangesHandler((status, reason) =>
            {
                Logger.LogInformation($"Detected change in connection status:{Environment.NewLine}Changed Status: {status} Reason: {reason}");
                if (status == ConnectionStatus.Disconnected_Retrying)
                {
                    this.twinTestState.EdgeHubLastStopped = DateTime.UtcNow;
                }
                else if (status == ConnectionStatus.Connected)
                {
                    this.twinTestState.EdgeHubLastStarted = DateTime.UtcNow;
                }
            });
        }
Beispiel #12
0
        /// <summary>
        /// Initializes the ModuleClient and sets up the callback to receive
        /// messages containing temperature information
        /// </summary>
        static async Task Init()
        {
            MqttTransportSettings mqttSetting = new MqttTransportSettings(TransportType.Mqtt_Tcp_Only);

            ITransportSettings[] settings = { mqttSetting };

            // Open a connection to the Edge runtime
            ModuleClient ioTHubModuleClient = await ModuleClient.CreateFromEnvironmentAsync(settings);

            await ioTHubModuleClient.OpenAsync();

            Console.WriteLine("IoT Hub module client initialized.");

            // Read the TemperatureThreshold value from the module twin's desired properties
            var moduleTwin = await ioTHubModuleClient.GetTwinAsync();

            await OnDesiredPropertiesUpdate(moduleTwin.Properties.Desired, ioTHubModuleClient);

            // Attach a callback for updates to the module twin's desired properties.
            await ioTHubModuleClient.SetDesiredPropertyUpdateCallbackAsync(OnDesiredPropertiesUpdate, null);

            ioTHubModuleClient.SetConnectionStatusChangesHandler(ConnectionStatusChangeHandler);


            _moduleClient = ioTHubModuleClient;

            #region for test

            //_timer = new Timer(DoWork);
            //_timer.Change(0, 1000);
            //Console.WriteLine("Timer start");

            #endregion

            // Register callback to be called when a message is received by the module
            await ioTHubModuleClient.SetInputMessageHandlerAsync("input1", PipeMessage, ioTHubModuleClient);
        }
Beispiel #13
0
        /// <summary>
        /// Initializes the ModuleClient
        /// </summary>
        static async Task <ModuleClient> Init()
        {
            var    transportType     = TransportType.Amqp_Tcp_Only;
            string transportProtocol = Environment.GetEnvironmentVariable("ClientTransportType");

            // The way the module connects to the EdgeHub can be controlled via the env variable. Either MQTT or AMQP
            if (!string.IsNullOrEmpty(transportProtocol))
            {
                switch (transportProtocol.ToUpper())
                {
                case "AMQP":
                    transportType = TransportType.Amqp_Tcp_Only;
                    break;

                case "MQTT":
                    transportType = TransportType.Mqtt_Tcp_Only;
                    break;

                default:
                    // Anything else: use default
                    Log.Warning($"Ignoring unknown TransportProtocol={transportProtocol}. Using default={transportType}");
                    break;
                }
            }

            // Open a connection to the Edge runtime
            ModuleClient moduleClient = await ModuleClient.CreateFromEnvironmentAsync(transportType);

            moduleClient.SetConnectionStatusChangesHandler(ConnectionStatusHandler);

            await moduleClient.OpenAsync();

            Log.Information($"Edge Hub module client initialized using {transportType}");

            return(moduleClient);
        }
        private async Task SendMessageModuleMuxedOverAmqp(
            Client.TransportType transport,
            int poolSize,
            int devicesCount,
            bool useSameDevice = false)
        {
            var transportSettings = new ITransportSettings[]
            {
                new AmqpTransportSettings(transport)
                {
                    AmqpConnectionPoolSettings = new AmqpConnectionPoolSettings()
                    {
                        MaxPoolSize = unchecked ((uint)poolSize),
                        Pooling     = true
                    }
                }
            };

            ICollection <ModuleClient>     moduleClients = new List <ModuleClient>();
            Dictionary <ModuleClient, int> moduleClientConnectionStatusChangeCount = new Dictionary <ModuleClient, int>();

            try
            {
                _log.WriteLine($"{nameof(MessageSendE2EMultiplexingTests)}: Starting the test execution for {devicesCount} modules");

                for (int i = 0; i < devicesCount; i++)
                {
                    ConnectionStatus?            lastConnectionStatus             = null;
                    ConnectionStatusChangeReason?lastConnectionStatusChangeReason = null;
                    int setConnectionStatusChangesHandlerCount = 0;

                    string devicePrefix = useSameDevice ? DevicePrefix : $"{DevicePrefix}_{i}_";
                    string modulePrefix = useSameDevice ? $"{ModulePrefix}_{i}_" : ModulePrefix;

                    TestModule testModule = await TestModule.GetTestModuleAsync(devicePrefix, modulePrefix).ConfigureAwait(false);

                    ModuleClient moduleClient = ModuleClient.CreateFromConnectionString(testModule.ConnectionString, transportSettings);
                    moduleClients.Add(moduleClient);

                    moduleClient.SetConnectionStatusChangesHandler((status, statusChangeReason) =>
                    {
                        setConnectionStatusChangesHandlerCount++;
                        lastConnectionStatus             = status;
                        lastConnectionStatusChangeReason = statusChangeReason;
                        _log.WriteLine($"{nameof(MessageSendE2EMultiplexingTests)}.{nameof(ConnectionStatusChangesHandler)}: status={status} statusChangeReason={statusChangeReason} count={setConnectionStatusChangesHandlerCount}");
                        moduleClientConnectionStatusChangeCount[moduleClient] = setConnectionStatusChangesHandlerCount;
                    });

                    _log.WriteLine($"{nameof(MessageSendE2EMultiplexingTests)}: Preparing to send message for module {i}");
                    await moduleClient.OpenAsync().ConfigureAwait(false);

                    await MessageSend.SendSingleMessageModuleAndVerifyAsync(moduleClient, testModule.DeviceId).ConfigureAwait(false);
                }
            }
            finally
            {
                // Close and dispose all of the module client instances here
                foreach (ModuleClient moduleClient in moduleClients)
                {
                    await moduleClient.CloseAsync().ConfigureAwait(false);

                    // The connection status change count should be 2: connect (open) and disabled (close)
                    Assert.IsTrue(moduleClientConnectionStatusChangeCount[moduleClient] == 2, $"Connection status change count for deviceClient {TestLogging.GetHashCode(moduleClient)} is {moduleClientConnectionStatusChangeCount[moduleClient]}");

                    _log.WriteLine($"{nameof(MessageSendE2EMultiplexingTests)}: Disposing moduleClient {TestLogging.GetHashCode(moduleClient)}");
                    moduleClient.Dispose();
                }
            }
        }
Beispiel #15
0
        async Task ModuleClient_Gives_ConnectionStatus_DeviceDisabled_Base(
            Client.TransportType protocol, Func <RegistryManager, string, Task> registryManagerOperation)
        {
            AmqpTransportSettings amqpTransportSettings = new AmqpTransportSettings(protocol);

            ITransportSettings[] transportSettings = new ITransportSettings[] { amqpTransportSettings };

            TestModule testModule = await TestModule.GetTestModuleAsync(DevicePrefix + $"_{Guid.NewGuid()}", ModulePrefix).ConfigureAwait(false);

            ConnectionStatus?            status             = null;
            ConnectionStatusChangeReason?statusChangeReason = null;
            int deviceDisabledReceivedCount = 0;
            ConnectionStatusChangesHandler statusChangeHandler = (s, r) =>
            {
                if (r == ConnectionStatusChangeReason.Device_Disabled)
                {
                    status             = s;
                    statusChangeReason = r;
                    deviceDisabledReceivedCount++;
                }
            };

            using (ModuleClient moduleClient = ModuleClient.CreateFromConnectionString(testModule.ConnectionString, transportSettings))
            {
                moduleClient.SetConnectionStatusChangesHandler(statusChangeHandler);
                _log.WriteLine($"Created {nameof(DeviceClient)} ID={TestLogging.IdOf(moduleClient)}");

                Console.WriteLine("ModuleClient OpenAsync.");
                await moduleClient.OpenAsync().ConfigureAwait(false);

                // Receiving the module twin should succeed right now.
                Console.WriteLine("ModuleClient GetTwinAsync.");
                var twin = await moduleClient.GetTwinAsync().ConfigureAwait(false);

                Assert.IsNotNull(twin);

                // Delete the device in IoT Hub.
                using (RegistryManager registryManager = RegistryManager.CreateFromConnectionString(Configuration.IoTHub.ConnectionString))
                {
                    await registryManagerOperation(registryManager, testModule.DeviceId).ConfigureAwait(false);
                }

                // Periodically keep retrieving the device twin to keep connection alive.
                // The ConnectionStatusChangesHandler should be triggered when the connection is closed from IoT hub with an
                // exception thrown.
                int twinRetrievals = 50;
                for (int i = 0; i < twinRetrievals; i++)
                {
                    try
                    {
                        await Task.Delay(TimeSpan.FromSeconds(10)).ConfigureAwait(false);

                        if (deviceDisabledReceivedCount == 1)
                        {
                            // Call an API on the client again to trigger the ConnectionStatusChangesHandler once again with the
                            // Device_Disabled status.
                            // This currently does not work due to some issues with IoT hub allowing new connections even when the
                            // device is deleted/disabled. Once that problem is investigated and fixed, we can re-enable this call
                            // and test for multiple invocations of the ConnectionStatusChangeHandler.
                            // await moduleClient.GetTwinAsync().ConfigureAwait(false);
                            break;
                        }
                    }
                    catch (IotHubException ex)
                    {
                        _log.WriteLine($"Exception occurred while retrieving module twin: {ex}");
                        Assert.IsInstanceOfType(ex.InnerException, typeof(DeviceNotFoundException));
                    }
                }

                Assert.AreEqual(1, deviceDisabledReceivedCount);
                Assert.AreEqual(ConnectionStatus.Disconnected, status);
                Assert.AreEqual(ConnectionStatusChangeReason.Device_Disabled, statusChangeReason);
            }
        }
        public async Task InitiateSimulationAsync()
        {
            string logPrefix = "system".BuildLogPrefix();

            try
            {
                //Connectivity tests
                //Control if a connection string exists (ideally, stored in TPM/HSM or any secured location.
                //If there is no connection string, check if the DPS settings are provided.
                //If so, provision the device and persist the connection string for upcoming boots.
                if (string.IsNullOrEmpty(ModuleSettings.ConnectionString))
                {
                    ModuleSettings.ConnectionString = await _provisioningService.AddModuleIdentityToDevice(ModuleSettings.ModuleId);

                    if (string.IsNullOrEmpty(ModuleSettings.ConnectionString))
                    {
                        _logger.LogWarning($"{logPrefix}::{ModuleSettings.ArtifactId}::No module connection string has been created.");
                    }
                    else
                    {
                        _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::Module connection string being persisted.");
                        await ConfigurationHelpers.WriteModulesSettings(ModuleSettings, _environmentName);
                    }
                }

                IoTTools.CheckModuleConnectionStringData(ModuleSettings.ConnectionString, _logger);

                // Connect to the IoT hub using the MQTT protocol
                _moduleClient = ModuleClient.CreateFromConnectionString(ModuleSettings.ConnectionString, Microsoft.Azure.Devices.Client.TransportType.Mqtt);
                _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::Module client created.");

                if (SimulationSettings.EnableTwinPropertiesDesiredChangesNotifications)
                {
                    await _moduleClient.SetDesiredPropertyUpdateCallbackAsync(OnDesiredPropertyChange, null);

                    _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::Twin Desired Properties update callback handler registered.");
                }

                //Configuration
                if (SimulationSettings.EnableC2DDirectMethods)
                {
                    //Register C2D Direct methods handlers
                    await RegisterC2DDirectMethodsHandlersAsync(_moduleClient, ModuleSettings, _logger);
                }

                if (SimulationSettings.EnableC2DMessages)
                {
                    //Start receiving C2D messages

                    ReceiveC2DMessagesAsync(_moduleClient, ModuleSettings, _logger);
                }

                //Messages
                if (SimulationSettings.EnableTelemetryMessages)
                {
                    SendDeviceToCloudMessagesAsync(_moduleClient, ModuleSettings.DeviceId, ModuleSettings.ModuleId, _logger); //interval is a global variable changed by processes
                }
                if (SimulationSettings.EnableErrorMessages)
                {
                    SendDeviceToCloudErrorAsync(_moduleClient, ModuleSettings.DeviceId, ModuleSettings.ModuleId, SimulationSettings.ErrorFrecuency, _logger);
                }

                if (SimulationSettings.EnableCommissioningMessages)
                {
                    SendDeviceToCloudCommissioningAsync(_moduleClient, ModuleSettings.DeviceId, ModuleSettings.ModuleId, SimulationSettings.CommissioningFrecuency, _logger);
                }

                if (SimulationSettings.EnableReadingTwinProperties)
                {
                    //Twins
                    _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::INITIALIZATION::Retrieving twin.");
                    Twin twin = await _moduleClient.GetTwinAsync();

                    if (twin != null)
                    {
                        _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::INITIALIZATION::Device twin: {JsonConvert.SerializeObject(twin, Formatting.Indented)}.");
                    }
                    else
                    {
                        _logger.LogDebug($"{logPrefix}::{ModuleSettings.ArtifactId}::INITIALIZATION::No device twin.");
                    }
                }

                _moduleClient.SetConnectionStatusChangesHandler(new ConnectionStatusChangesHandler(ConnectionStatusChanged));
            }
            catch (ConnectionStringException ex)
            {
                _logger.LogError($"{logPrefix}::{ModuleSettings.ArtifactId}::ConnectionStringException:{ex.Message}");
            }
            catch (Exception ex)
            {
                _logger.LogError($"{logPrefix}::{ModuleSettings.ArtifactId}::{ex.Message}");
            }
        }
Beispiel #17
0
        static async Task <int> MainAsync()
        {
            try
            {
                Logger.LogInformation("Validate Metrics Main() started.");

                (CancellationTokenSource cts, ManualResetEventSlim completed, Option <object> handler) = ShutdownHandler.Init(TimeSpan.FromSeconds(5), Logger);

                IConfiguration configuration = new ConfigurationBuilder()
                                               .SetBasePath(Directory.GetCurrentDirectory())
                                               .AddJsonFile("config/appsettings.json", optional: true)
                                               .AddEnvironmentVariables()
                                               .Build();

                var transportType = configuration.GetValue("ClientTransportType", Microsoft.Azure.Devices.Client.TransportType.Mqtt);

                Logger.LogInformation("Make Client");
                using (ModuleClient moduleClient = await ModuleUtil.CreateModuleClientAsync(
                           transportType,
                           new ClientOptions(),
                           ModuleUtil.DefaultTimeoutErrorDetectionStrategy,
                           ModuleUtil.DefaultTransientRetryStrategy,
                           Logger))
                    using (MetricsScraper scraper = new MetricsScraper(new List <string> {
                        "http://edgeHub:9600/metrics", "http://edgeAgent:9600/metrics"
                    }))
                    {
                        Logger.LogInformation("Open Async");
                        await moduleClient.OpenAsync();

                        Logger.LogInformation("Set method handler");
                        await moduleClient.SetMethodHandlerAsync(
                            "ValidateMetrics",
                            async (MethodRequest methodRequest, object _) =>
                        {
                            Logger.LogInformation("Validating metrics");

                            TestReporter testReporter = new TestReporter("Metrics Validation");
                            List <TestBase> tests     = new List <TestBase>
                            {
                                new ValidateMessages(testReporter, scraper, moduleClient, transportType),
                                new ValidateDocumentedMetrics(testReporter, scraper, moduleClient),
                                // new ValidateHostRanges(testReporter, scraper, moduleClient),
                            };

                            using (testReporter.MeasureDuration())
                            {
                                await Task.WhenAll(tests.Select(test => test.Start(cts.Token)));
                            }

                            var result = new MethodResponse(Encoding.UTF8.GetBytes(testReporter.ReportResults()), (int)HttpStatusCode.OK);

                            Logger.LogInformation($"Finished validating metrics. Result size: {result.Result.Length}");
                            return(result);
                        },
                            null);

                        moduleClient.SetConnectionStatusChangesHandler((status, reason)
                                                                       => Logger.LogWarning($"Module to Edge Hub connection changed Status: {status} Reason: {reason}"));

                        Logger.LogInformation("Ready to validate metrics");
                        await cts.Token.WhenCanceled();
                    }

                completed.Set();
                handler.ForEach(h => GC.KeepAlive(h));
                Logger.LogInformation("Validate Metrics Main() finished.");
            }
            catch (Exception e)
            {
                Logger.LogError(e.ToString());
            }

            return(0);
        }
 /// <inheritdoc />
 public void SetConnectionStatusChangesHandler(ConnectionStatusChangesHandler statusChangesHandler)
 {
     _client.SetConnectionStatusChangesHandler(statusChangesHandler);
 }