示例#1
0
        private async Task SendMethodAndRespondAsync(
            Client.TransportType transport,
            Func <DeviceClient, string, MsTestLogger, Task <Task> > setDeviceReceiveMethod,
            TimeSpan responseTimeout = default,
            ServiceClientTransportSettings serviceClientTransportSettings = default)
        {
            using TestDevice testDevice = await TestDevice.GetTestDeviceAsync(Logger, _devicePrefix).ConfigureAwait(false);

            using var deviceClient = DeviceClient.CreateFromConnectionString(testDevice.ConnectionString, transport);

            Task methodReceivedTask = await setDeviceReceiveMethod(deviceClient, MethodName, Logger).ConfigureAwait(false);

            Task serviceSendTask = ServiceSendMethodAndVerifyResponseAsync(
                testDevice.Id,
                MethodName,
                DeviceResponseJson,
                ServiceRequestJson,
                Logger,
                responseTimeout,
                serviceClientTransportSettings);

            await Task.WhenAll(serviceSendTask, methodReceivedTask).ConfigureAwait(false);

            await deviceClient.CloseAsync().ConfigureAwait(false);
        }
示例#2
0
        protected async Task VerifyDirectMethodAsync()
        {
            // User Service SDK to invoke Direct Method on the device.
            var settings = new ServiceClientTransportSettings();

            this.proxy.ForEach(p => settings.HttpProxy = p);
            ServiceClient serviceClient =
                ServiceClient.CreateFromConnectionString(this.context.IotHubConnectionString, this.serviceClientTransportType, settings);

            // Call a direct method
            using (var cts = new CancellationTokenSource(TimeSpan.FromSeconds(300)))
            {
                CloudToDeviceMethod cloudToDeviceMethod = new CloudToDeviceMethod("DirectMethod").SetPayloadJson("{\"TestKey\" : \"TestValue\"}");

                CloudToDeviceMethodResult result = await serviceClient.InvokeDeviceMethodAsync(
                    this.context.Device.Id,
                    cloudToDeviceMethod,
                    cts.Token);

                if (result.Status != 200)
                {
                    throw new Exception($"Could not invoke Direct Method on Device with result status {result.Status}.");
                }

                if (!result.GetPayloadAsJson().Equals("{\"TestKey\":\"TestValue\"}", StringComparison.Ordinal))
                {
                    throw new Exception($"Payload doesn't match with Sent Payload. Received payload: {result.GetPayloadAsJson()}. Expected: {{\"TestKey\":\"TestValue\"}}");
                }
            }
        }
示例#3
0
        public static async Task ServiceSendMethodAndVerifyResponseAsync(
            string deviceId,
            string moduleId,
            string methodName,
            string respJson,
            string reqJson,
            MsTestLogger logger,
            TimeSpan responseTimeout = default,
            ServiceClientTransportSettings serviceClientTransportSettings = default)
        {
            ServiceClient serviceClient = serviceClientTransportSettings == default
                ? ServiceClient.CreateFromConnectionString(TestConfiguration.IoTHub.ConnectionString)
                : ServiceClient.CreateFromConnectionString(TestConfiguration.IoTHub.ConnectionString, TransportType.Amqp, serviceClientTransportSettings);

            TimeSpan methodTimeout = responseTimeout == default ? s_defaultMethodTimeoutMinutes : responseTimeout;

            logger.Trace($"{nameof(ServiceSendMethodAndVerifyResponseAsync)}: Invoke method {methodName}.");
            CloudToDeviceMethodResult response =
                await serviceClient.InvokeDeviceMethodAsync(
                    deviceId,
                    moduleId,
                    new CloudToDeviceMethod(methodName, responseTimeout).SetPayloadJson(reqJson)).ConfigureAwait(false);

            logger.Trace($"{nameof(ServiceSendMethodAndVerifyResponseAsync)}: Method status: {response.Status}.");
            Assert.AreEqual(200, response.Status, $"The expected response status should be 200 but was {response.Status}");
            string payload = response.GetPayloadAsJson();

            Assert.AreEqual(respJson, payload, $"The expected response payload should be {respJson} but was {payload}");

            await serviceClient.CloseAsync().ConfigureAwait(false);

            serviceClient.Dispose();
        }
示例#4
0
        public static async Task ServiceSendMethodAndVerifyNotReceivedAsync(
            string deviceId,
            string methodName,
            MsTestLogger logger,
            TimeSpan responseTimeout = default,
            ServiceClientTransportSettings serviceClientTransportSettings = default)
        {
            ServiceClient serviceClient = serviceClientTransportSettings == default
                ? ServiceClient.CreateFromConnectionString(TestConfiguration.IoTHub.ConnectionString)
                : ServiceClient.CreateFromConnectionString(TestConfiguration.IoTHub.ConnectionString, TransportType.Amqp, serviceClientTransportSettings);

            TimeSpan methodTimeout = responseTimeout == default ? s_defaultMethodTimeoutMinutes : responseTimeout;

            logger.Trace($"{nameof(ServiceSendMethodAndVerifyResponseAsync)}: Invoke method {methodName}.");
            try
            {
                CloudToDeviceMethodResult response = await serviceClient
                                                     .InvokeDeviceMethodAsync(
                    deviceId,
                    new CloudToDeviceMethod(methodName, methodTimeout).SetPayloadJson(null))
                                                     .ConfigureAwait(false);
            }
            catch (DeviceNotFoundException)
            {
            }
            finally
            {
                await serviceClient.CloseAsync().ConfigureAwait(false);

                serviceClient.Dispose();
            }
        }
        public async Task ServiceClient_Message_SendSingleMessage_WithProxy()
        {
            ServiceClientTransportSettings transportSettings = new ServiceClientTransportSettings();

            transportSettings.AmqpProxy = new WebProxy(s_proxyServerAddress);
            transportSettings.HttpProxy = new WebProxy(s_proxyServerAddress);

            await SendSingleMessageService(transportSettings).ConfigureAwait(false);
        }
        public async Task Method_ServiceSendsMethodThroughProxyWithCustomTimeout()
        {
            ServiceClientTransportSettings serviceClientTransportSettings = new ServiceClientTransportSettings
            {
                HttpProxy = new WebProxy(Configuration.IoTHub.ProxyServerAddress)
            };

            await SendMethodAndRespond(Client.TransportType.Mqtt_Tcp_Only, SetDeviceReceiveMethod, TimeSpan.FromMinutes(5), serviceClientTransportSettings).ConfigureAwait(false);
        }
示例#7
0
        protected async Task VerifyDirectMethodAsync()
        {
            // User Service SDK to invoke Direct Method on the device.
            var settings = new ServiceClientTransportSettings();

            this.proxy.ForEach(p => settings.HttpProxy = p);
            ServiceClient serviceClient =
                ServiceClient.CreateFromConnectionString(this.context.IotHubConnectionString, this.serviceClientTransportType, settings);

            // Call a direct method
            TimeSpan testDuration = TimeSpan.FromSeconds(300);
            DateTime endTime      = DateTime.UtcNow + testDuration;

            using (var cts = new CancellationTokenSource(testDuration))
            {
                CloudToDeviceMethod cloudToDeviceMethod = new CloudToDeviceMethod("DirectMethod").SetPayloadJson("{\"TestKey\" : \"TestValue\"}");

                CloudToDeviceMethodResult result = null;
                bool isRetrying = true;
                while (isRetrying)
                {
                    try
                    {
                        result = await serviceClient.InvokeDeviceMethodAsync(
                            this.context.Device.Id,
                            cloudToDeviceMethod,
                            cts.Token);
                    }
                    catch (Exception ex)
                    {
                        if (DateTime.UtcNow >= endTime)
                        {
                            Console.WriteLine($"Failed to send direct method from device '{this.context.Device.Id}' with payload '{cloudToDeviceMethod}: {ex}'");
                            isRetrying = false;
                        }
                        else
                        {
                            Console.WriteLine($"Failed to send direct method from device '{this.context.Device.Id}' with payload '{cloudToDeviceMethod}: {ex.Message}'");
                        }
                    }
                }

                if (result?.Status != 200)
                {
                    throw new Exception($"Could not invoke Direct Method on Device with result status {result?.Status}.");
                }

                if (!result.GetPayloadAsJson().Equals("{\"TestKey\":\"TestValue\"}", StringComparison.Ordinal))
                {
                    throw new Exception($"Payload doesn't match with Sent Payload. Received payload: {result.GetPayloadAsJson()}. Expected: {{\"TestKey\":\"TestValue\"}}");
                }
            }
        }
        private async Task SendSingleMessageService(ServiceClientTransportSettings transportSettings)
        {
            TestDevice testDevice = await TestDevice.GetTestDeviceAsync(DevicePrefix).ConfigureAwait(false);

            DeviceClient deviceClient = DeviceClient.CreateFromConnectionString(testDevice.ConnectionString);

            ServiceClient serviceClient = ServiceClient.CreateFromConnectionString(ConnectionString, TransportType.Amqp, transportSettings);

            string  payload;
            string  p1Value;
            Message testMessage = ComposeD2CTestMessage(out payload, out p1Value);
            await serviceClient.SendAsync(testDevice.Id, testMessage).ConfigureAwait(false);
        }
示例#9
0
        public async Task Method_ServiceSendsMethodThroughProxyWithDefaultTimeout()
        {
            var serviceClientTransportSettings = new ServiceClientTransportSettings
            {
                HttpProxy = new WebProxy(TestConfiguration.IoTHub.ProxyServerAddress)
            };

            await SendMethodAndRespondAsync(
                Client.TransportType.Mqtt_Tcp_Only,
                SetDeviceReceiveMethodAsync,
                serviceClientTransportSettings : serviceClientTransportSettings)
            .ConfigureAwait(false);
        }
        private async Task SendSingleMessageService(ServiceClientTransportSettings transportSettings)
        {
            TestDevice testDevice = await TestDevice.GetTestDeviceAsync(Logger, DevicePrefix).ConfigureAwait(false);

            using (DeviceClient deviceClient = DeviceClient.CreateFromConnectionString(testDevice.ConnectionString))
                using (ServiceClient serviceClient = ServiceClient.CreateFromConnectionString(s_connectionString, TransportType.Amqp, transportSettings))
                {
                    (Message testMessage, string messageId, string payload, string p1Value) = ComposeD2CTestMessage();
                    await serviceClient.SendAsync(testDevice.Id, testMessage).ConfigureAwait(false);

                    await deviceClient.CloseAsync().ConfigureAwait(false);

                    await serviceClient.CloseAsync().ConfigureAwait(false);
                }
        }
示例#11
0
        protected async Task VerifyEdgeAgentIsConnectedToIotHub()
        {
            Console.WriteLine("Verifying if edge is connected to IoThub");
            using (var cts = new CancellationTokenSource(TimeSpan.FromSeconds(300)))
            {
                Exception savedException = null;

                try
                {
                    var settings = new ServiceClientTransportSettings();
                    this.proxy.ForEach(p => settings.HttpProxy = p);

                    ServiceClient serviceClient =
                        ServiceClient.CreateFromConnectionString(this.context.IotHubConnectionString, this.serviceClientTransportType, settings);

                    while (true)
                    {
                        await Task.Delay(TimeSpan.FromSeconds(10), cts.Token);

                        try
                        {
                            CloudToDeviceMethodResult result = await serviceClient.InvokeDeviceMethodAsync(
                                this.context.DeviceId,
                                "$edgeAgent",
                                new CloudToDeviceMethod("ping"),
                                cts.Token);

                            if (result.Status == 200)
                            {
                                break;
                            }
                        }
                        catch (Exception e)
                        {
                            savedException = e;
                        }
                    }
                }
                catch (OperationCanceledException e)
                {
                    throw new Exception($"Failed to ping $edgeAgent from the cloud: {savedException?.Message ?? e.Message}");
                }
                catch (Exception e)
                {
                    throw new Exception($"Failed to ping $edgeAgent from the cloud: {e.Message}");
                }
            }
        }
示例#12
0
        private async Task SendMethodAndUnsubscribeAsync(
            Client.TransportType transport,
            Func <DeviceClient,
                  string, MsTestLogger,
                  Task <Task> > subscribeAndUnsubscribeMethod,
            TimeSpan responseTimeout = default,
            ServiceClientTransportSettings serviceClientTransportSettings = default)
        {
            using TestDevice testDevice = await TestDevice.GetTestDeviceAsync(Logger, _devicePrefix).ConfigureAwait(false);

            using var deviceClient = DeviceClient.CreateFromConnectionString(testDevice.ConnectionString, transport);

            await subscribeAndUnsubscribeMethod(deviceClient, MethodName, Logger).ConfigureAwait(false);

            await ServiceSendMethodAndVerifyNotReceivedAsync(testDevice.Id, MethodName, Logger, responseTimeout, serviceClientTransportSettings).ConfigureAwait(false);

            await deviceClient.CloseAsync().ConfigureAwait(false);
        }
示例#13
0
        public IotHub(string iotHubConnectionString, string eventHubEndpoint, Option <Uri> proxyUri)
        {
            this.eventHubEndpoint       = eventHubEndpoint;
            this.iotHubConnectionString = iotHubConnectionString;
            Option <IWebProxy> proxy = proxyUri.Map(p => new WebProxy(p) as IWebProxy);

            this.registryManager = new Lazy <RegistryManager>(
                () =>
            {
                var settings = new HttpTransportSettings();
                proxy.ForEach(p => settings.Proxy = p);
                return(RegistryManager.CreateFromConnectionString(
                           this.iotHubConnectionString,
                           settings));
            });

            this.serviceClient = new Lazy <ServiceClient>(
                () =>
            {
                var settings = new ServiceClientTransportSettings();
                proxy.ForEach(p => settings.HttpProxy = p);
                return(ServiceClient.CreateFromConnectionString(
                           this.iotHubConnectionString,
                           DeviceTransportType.Amqp_WebSocket_Only,
                           settings));
            });

            this.eventHubClient = new Lazy <EventHubClient>(
                () =>
            {
                var builder = new EventHubsConnectionStringBuilder(this.eventHubEndpoint)
                {
                    TransportType = EventHubTransportType.AmqpWebSockets
                };
                var client = EventHubClient.CreateFromConnectionString(builder.ToString());
                proxy.ForEach(p => client.WebProxy = p);
                return(client);
            });
        }
        public static async Task ServiceSendMethodAndVerifyResponse(string deviceName, string methodName, string respJson, string reqJson, TimeSpan responseTimeout, ServiceClientTransportSettings serviceClientTransportSettings)
        {
            using (ServiceClient serviceClient = ServiceClient.CreateFromConnectionString(Configuration.IoTHub.ConnectionString, TransportType.Amqp, serviceClientTransportSettings))
            {
                _log.WriteLine($"{nameof(ServiceSendMethodAndVerifyResponse)}: Invoke method {methodName}.");
                CloudToDeviceMethodResult response =
                    await serviceClient.InvokeDeviceMethodAsync(
                        deviceName,
                        new CloudToDeviceMethod(methodName, responseTimeout).SetPayloadJson(reqJson)).ConfigureAwait(false);

                _log.WriteLine($"{nameof(ServiceSendMethodAndVerifyResponse)}: Method status: {response.Status}.");
                Assert.AreEqual(200, response.Status, $"The expected response status should be 200 but was {response.Status}");
                string payload = response.GetPayloadAsJson();
                Assert.AreEqual(respJson, payload, $"The expected response payload should be {respJson} but was {payload}");

                await serviceClient.CloseAsync().ConfigureAwait(false);
            }
        }
 private async Task SendMethodAndRespond(Client.TransportType transport, Func <DeviceClient, string, Task <Task> > setDeviceReceiveMethod, ServiceClientTransportSettings serviceClientTransportSettings)
 {
     await SendMethodAndRespond(transport, setDeviceReceiveMethod, DefaultMethodTimeoutMinutes, serviceClientTransportSettings).ConfigureAwait(false);
 }
        private async Task SendMethodAndRespond(Client.TransportType transport, Func <DeviceClient, string, Task <Task> > setDeviceReceiveMethod, TimeSpan responseTimeout, ServiceClientTransportSettings serviceClientTransportSettings)
        {
            TestDevice testDevice = await TestDevice.GetTestDeviceAsync(DevicePrefix).ConfigureAwait(false);

            using (DeviceClient deviceClient = DeviceClient.CreateFromConnectionString(testDevice.ConnectionString, transport))
            {
                Task methodReceivedTask = await setDeviceReceiveMethod(deviceClient, MethodName).ConfigureAwait(false);

                await Task.WhenAll(
                    ServiceSendMethodAndVerifyResponse(testDevice.Id, MethodName, DeviceResponseJson, ServiceRequestJson, responseTimeout, serviceClientTransportSettings),
                    methodReceivedTask).ConfigureAwait(false);

                await deviceClient.CloseAsync().ConfigureAwait(false);
            }
        }
示例#17
0
        protected async Task VerifyDirectMethodAsync()
        {
            // User Service SDK to invoke Direct Method on the device.
            var settings = new ServiceClientTransportSettings();

            this.proxy.ForEach(p => settings.HttpProxy = p);
            ServiceClient serviceClient =
                ServiceClient.CreateFromConnectionString(this.context.IotHubConnectionString, this.serviceClientTransportType, settings);

            // Call a direct method
            TimeSpan testDuration = TimeSpan.FromSeconds(300);
            DateTime endTime      = DateTime.UtcNow + testDuration;

            CloudToDeviceMethod cloudToDeviceMethod = new CloudToDeviceMethod("DirectMethod").SetPayloadJson("{\"TestKey\" : \"TestValue\"}");

            CloudToDeviceMethodResult result = null;
            // To reduce log size and make troubleshooting easier, log last exception only.
            Exception lastException = null;
            bool      isRetrying    = true;

            Console.WriteLine("Starting Direct method test.");
            while (isRetrying && DateTime.UtcNow <= endTime)
            {
                try
                {
                    using (var cts = new CancellationTokenSource(TimeSpan.FromSeconds(10)))
                    {
                        result = await serviceClient.InvokeDeviceMethodAsync(
                            this.context.Device.Id,
                            cloudToDeviceMethod,
                            cts.Token);

                        if (result?.Status == 200)
                        {
                            isRetrying = false;
                        }

                        // Don't retry too fast
                        await Task.Delay(1000, cts.Token);
                    }
                }
                catch (OperationCanceledException ex)
                {
                    if (lastException == null)
                    {
                        lastException = ex;
                    }
                }
                catch (Exception ex)
                {
                    lastException = ex;
                }
            }

            if (result?.Status != 200)
            {
                if (lastException != null)
                {
                    Console.WriteLine($"Failed to send direct method from device '{this.context.Device.Id}' with payload '{cloudToDeviceMethod}: {lastException}'");
                }

                throw new Exception($"Could not invoke Direct Method on Device with result status {result?.Status}.");
            }

            if (!result.GetPayloadAsJson().Equals("{\"TestKey\":\"TestValue\"}", StringComparison.Ordinal))
            {
                throw new Exception($"Payload doesn't match with Sent Payload. Received payload: {result.GetPayloadAsJson()}. Expected: {{\"TestKey\":\"TestValue\"}}");
            }

            Console.WriteLine("Direct method test passed.");
        }