Skip to content

Commit 87e5996

Browse files
authored
Add support for message with content type and user properties (#263)
1 parent ed01470 commit 87e5996

File tree

10 files changed

+448
-4
lines changed

10 files changed

+448
-4
lines changed

.runsettings

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
<?xml version="1.0" encoding="utf-8"?>
2+
<RunSettings>
3+
<!-- Configurations that affect the Test Framework -->
4+
<RunConfiguration>
5+
<MaxCpuCount>1</MaxCpuCount>
6+
<ResultsDirectory>.\TestResults</ResultsDirectory><!-- Path relative to solution directory -->
7+
<TestSessionTimeout>120000</TestSessionTimeout><!-- Milliseconds -->
8+
<TargetFrameworkVersion>net48</TargetFrameworkVersion>
9+
<TargetPlatform>x64</TargetPlatform>
10+
</RunConfiguration>
11+
<nanoFrameworkAdapter>
12+
<Logging>None</Logging>
13+
<IsRealHardware>False</IsRealHardware>
14+
</nanoFrameworkAdapter>
15+
</RunSettings>
Lines changed: 87 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,87 @@
1+
//
2+
// Copyright (c) .NET Foundation and Contributors
3+
// See LICENSE file in the project root for full license information.
4+
//
5+
6+
using nanoFramework.Azure.Devices.Client;
7+
using nanoFramework.M2Mqtt.Messages;
8+
using nanoFramework.TestFramework;
9+
using System;
10+
using System.Collections;
11+
12+
namespace DeviceClientTests
13+
{
14+
[TestClass]
15+
public class DeviceClientTests
16+
{
17+
private static string _propertyOneName = "prop1";
18+
private static string _propertyTwoName = "prop2";
19+
private static string _propertyThreeName = "prop3";
20+
private static string _propertyOneValue = "iAmValue1";
21+
private static float _propertyTwoValue = 33.44f;
22+
private static string _propertyThreeValue = "string with $/#% chars";
23+
24+
private static UserProperty _userProperty1 = new(_propertyOneName, _propertyOneValue);
25+
private static UserProperty _userProperty2 = new(_propertyTwoName, _propertyTwoValue.ToString());
26+
private static UserProperty _userProperty3 = new(_propertyThreeName, _propertyThreeValue);
27+
28+
private static UserProperty _userPropertyBad1 = new(null, _propertyOneValue);
29+
private static UserProperty _userPropertyBad2 = new(_propertyTwoName, null);
30+
31+
[TestMethod]
32+
public void EncodeUserPropertiesTest_00()
33+
{
34+
DeviceClient client = new();
35+
36+
var encodedProperties = client.EncodeUserProperties(new ArrayList() { _userProperty1, _userProperty2, _userProperty3 });
37+
38+
Assert.Equal(encodedProperties, "prop1=iAmValue1&prop2=33.44&prop3=string+with+%24%2F%23%25+chars");
39+
}
40+
41+
[TestMethod]
42+
public void EncodeUserPropertiesTest_01()
43+
{
44+
DeviceClient client = new();
45+
46+
Assert.Throws(typeof(ArgumentException), () =>
47+
{
48+
client.EncodeUserProperties(new ArrayList() { _userProperty3, _userPropertyBad1 });
49+
},
50+
"Expecting ArgumentException with invalid user property 01."
51+
);
52+
53+
Assert.Throws(typeof(ArgumentException), () =>
54+
{
55+
client.EncodeUserProperties(new ArrayList() { _userPropertyBad2, _userProperty3 });
56+
},
57+
"Expecting ArgumentException with invalid user property 02."
58+
);
59+
60+
Assert.Throws(typeof(InvalidCastException), () =>
61+
{
62+
client.EncodeUserProperties(new ArrayList() { _userProperty1, "Invalid property" });
63+
},
64+
"Expecting ArgumentException with invalid user property 03."
65+
);
66+
67+
Assert.Throws(typeof(InvalidCastException), () =>
68+
{
69+
client.EncodeUserProperties(new ArrayList() { 8888888, "Invalid property" });
70+
},
71+
"Expecting ArgumentException with invalid user property 04."
72+
);
73+
}
74+
75+
[DataRow("application/json", "$.ct=application%2Fjson&$.ce=utf-8")]
76+
[DataRow("application/mime", "$.ct=application%2Fmime&$.ce=utf-8")]
77+
[TestMethod]
78+
public void EncodeContentType_00(string contentType, string encodedContentType)
79+
{
80+
DeviceClient client = new();
81+
82+
Assert.Equal(
83+
client.EncodeContentType(contentType),
84+
encodedContentType);
85+
}
86+
}
87+
}
Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,94 @@
1+
<?xml version="1.0" encoding="utf-8"?>
2+
<Project ToolsVersion="Current" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
3+
<PropertyGroup Label="Globals">
4+
<NanoFrameworkProjectSystemPath>$(MSBuildExtensionsPath)\nanoFramework\v1.0\</NanoFrameworkProjectSystemPath>
5+
</PropertyGroup>
6+
<Import Project="$(NanoFrameworkProjectSystemPath)NFProjectSystem.Default.props" Condition="Exists('$(NanoFrameworkProjectSystemPath)NFProjectSystem.Default.props')" />
7+
<ItemGroup>
8+
<ProjectCapability Include="TestContainer" />
9+
</ItemGroup>
10+
<PropertyGroup>
11+
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
12+
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
13+
<ProjectTypeGuids>{11A8DD76-328B-46DF-9F39-F559912D0360};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}</ProjectTypeGuids>
14+
<ProjectGuid>557ef898-6cf2-4cbc-ae29-72f387ff0ee0</ProjectGuid>
15+
<OutputType>Library</OutputType>
16+
<AppDesignerFolder>Properties</AppDesignerFolder>
17+
<FileAlignment>512</FileAlignment>
18+
<RootNamespace>DeviceClientTests</RootNamespace>
19+
<AssemblyName>NFUnitTest</AssemblyName>
20+
<IsCodedUITest>False</IsCodedUITest>
21+
<IsTestProject>true</IsTestProject>
22+
<TestProjectType>UnitTest</TestProjectType>
23+
<TargetFrameworkVersion>v1.0</TargetFrameworkVersion>
24+
</PropertyGroup>
25+
<PropertyGroup>
26+
<SignAssembly>true</SignAssembly>
27+
</PropertyGroup>
28+
<PropertyGroup>
29+
<AssemblyOriginatorKeyFile>..\..\nanoFramework.Azure.Devices.Client\key.snk</AssemblyOriginatorKeyFile>
30+
</PropertyGroup>
31+
<PropertyGroup>
32+
<DelaySign>false</DelaySign>
33+
</PropertyGroup>
34+
<Import Project="$(NanoFrameworkProjectSystemPath)NFProjectSystem.props" Condition="Exists('$(NanoFrameworkProjectSystemPath)NFProjectSystem.props')" />
35+
<ItemGroup>
36+
<Compile Include="DeviceClientTests.cs" />
37+
<Compile Include="Properties\AssemblyInfo.cs" />
38+
</ItemGroup>
39+
<ItemGroup>
40+
<Reference Include="mscorlib">
41+
<HintPath>..\..\packages\nanoFramework.CoreLibrary.1.12.0\lib\mscorlib.dll</HintPath>
42+
</Reference>
43+
<Reference Include="nanoFramework.M2Mqtt">
44+
<HintPath>..\..\packages\nanoFramework.M2Mqtt.5.1.59\lib\nanoFramework.M2Mqtt.dll</HintPath>
45+
</Reference>
46+
<Reference Include="nanoFramework.Runtime.Events">
47+
<HintPath>..\..\packages\nanoFramework.Runtime.Events.1.11.1\lib\nanoFramework.Runtime.Events.dll</HintPath>
48+
</Reference>
49+
<Reference Include="nanoFramework.Runtime.Native">
50+
<HintPath>..\..\packages\nanoFramework.Runtime.Native.1.5.4\lib\nanoFramework.Runtime.Native.dll</HintPath>
51+
</Reference>
52+
<Reference Include="nanoFramework.System.Collections">
53+
<HintPath>..\..\packages\nanoFramework.System.Collections.1.4.0\lib\nanoFramework.System.Collections.dll</HintPath>
54+
</Reference>
55+
<Reference Include="nanoFramework.System.Text">
56+
<HintPath>..\..\packages\nanoFramework.System.Text.1.2.22\lib\nanoFramework.System.Text.dll</HintPath>
57+
</Reference>
58+
<Reference Include="nanoFramework.TestFramework">
59+
<HintPath>..\..\packages\nanoFramework.TestFramework.2.0.60\lib\nanoFramework.TestFramework.dll</HintPath>
60+
</Reference>
61+
<Reference Include="nanoFramework.UnitTestLauncher">
62+
<HintPath>..\..\packages\nanoFramework.TestFramework.2.0.60\lib\nanoFramework.UnitTestLauncher.exe</HintPath>
63+
</Reference>
64+
<Reference Include="System.IO.Streams">
65+
<HintPath>..\..\packages\nanoFramework.System.IO.Streams.1.1.27\lib\System.IO.Streams.dll</HintPath>
66+
</Reference>
67+
<Reference Include="System.Net">
68+
<HintPath>..\..\packages\nanoFramework.System.Net.1.10.38\lib\System.Net.dll</HintPath>
69+
</Reference>
70+
<Reference Include="System.Threading">
71+
<HintPath>..\..\packages\nanoFramework.System.Threading.1.1.8\lib\System.Threading.dll</HintPath>
72+
</Reference>
73+
</ItemGroup>
74+
<ItemGroup>
75+
<None Include="packages.config" />
76+
</ItemGroup>
77+
<ItemGroup>
78+
<ProjectReference Include="..\..\nanoFramework.Azure.Devices.Client\Azure.Devices.Client.nfproj" />
79+
</ItemGroup>
80+
<Import Project="$(NanoFrameworkProjectSystemPath)NFProjectSystem.CSharp.targets" Condition="Exists('$(NanoFrameworkProjectSystemPath)NFProjectSystem.CSharp.targets')" />
81+
<!-- MANUAL UPDATE HERE -->
82+
<Import Project="..\..\packages\nanoFramework.TestFramework.2.0.60\build\nanoFramework.TestFramework.targets" Condition="Exists('..\..\packages\nanoFramework.TestFramework.2.0.60\build\nanoFramework.TestFramework.targets')" />
83+
<ProjectExtensions>
84+
<ProjectCapabilities>
85+
<ProjectConfigurationsDeclaredAsItems />
86+
</ProjectCapabilities>
87+
</ProjectExtensions>
88+
<Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
89+
<PropertyGroup>
90+
<WarningText>Update the Import path in nfproj to the correct nanoFramework.TestFramework NuGet package folder.</WarningText>
91+
</PropertyGroup>
92+
<Warning Condition="!Exists('..\..\packages\nanoFramework.TestFramework.2.0.60\build\nanoFramework.TestFramework.targets')" Text="'$(WarningText)'" />
93+
</Target>
94+
</Project>
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
using System.Reflection;
2+
using System.Runtime.CompilerServices;
3+
using System.Runtime.InteropServices;
4+
5+
// General Information about an assembly is controlled through the following
6+
// set of attributes. Change these attribute values to modify the information
7+
// associated with an assembly.
8+
[assembly: AssemblyDescription("")]
9+
[assembly: AssemblyConfiguration("")]
10+
[assembly: AssemblyCompany("")]
11+
[assembly: AssemblyCopyright("Copyright (c) 2021 nanoFramework contributors")]
12+
[assembly: AssemblyTrademark("")]
13+
[assembly: AssemblyCulture("")]
14+
15+
// Setting ComVisible to false makes the types in this assembly not visible
16+
// to COM components. If you need to access a type in this assembly from
17+
// COM, set the ComVisible attribute to true on that type.
18+
[assembly: ComVisible(false)]
19+
20+
// Version information for an assembly consists of the following four values:
21+
//
22+
// Major Version
23+
// Minor Version
24+
// Build Number
25+
// Revision
26+
//
27+
// You can specify all the values or you can default the Build and Revision Numbers
28+
// by using the '*' as shown below:
29+
// [assembly: AssemblyVersion("1.0.*")]
30+
[assembly: AssemblyVersion("1.0.0.0")]
31+
[assembly: AssemblyFileVersion("1.0.0.0")]
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
<?xml version="1.0" encoding="utf-8"?>
2+
<packages>
3+
<package id="nanoFramework.CoreLibrary" version="1.12.0" targetFramework="netnano1.0" />
4+
<package id="nanoFramework.M2Mqtt" version="5.1.59" targetFramework="netnano1.0" />
5+
<package id="nanoFramework.Runtime.Events" version="1.11.1" targetFramework="netnano1.0" />
6+
<package id="nanoFramework.Runtime.Native" version="1.5.4" targetFramework="netnano1.0" />
7+
<package id="nanoFramework.System.Collections" version="1.4.0" targetFramework="netnano1.0" />
8+
<package id="nanoFramework.System.IO.Streams" version="1.1.27" targetFramework="netnano1.0" />
9+
<package id="nanoFramework.System.Net" version="1.10.38" targetFramework="netnano1.0" />
10+
<package id="nanoFramework.System.Text" version="1.2.22" targetFramework="netnano1.0" />
11+
<package id="nanoFramework.System.Threading" version="1.1.8" targetFramework="netnano1.0" />
12+
<package id="nanoFramework.TestFramework" version="2.0.60" targetFramework="netnano1.0" developmentDependency="true" />
13+
</packages>
Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
{
2+
"version": 1,
3+
"dependencies": {
4+
".NETnanoFramework,Version=v1.0": {
5+
"nanoFramework.CoreLibrary": {
6+
"type": "Direct",
7+
"requested": "[1.12.0, 1.12.0]",
8+
"resolved": "1.12.0",
9+
"contentHash": "qQrFNXmJiStMC4VXk5cVMOJp23/qlT9FW5i9i+igwQVwraQTtvpkam8yK1hj992jqrbjoCIFZP4Hw9E8H0pB7w=="
10+
},
11+
"nanoFramework.M2Mqtt": {
12+
"type": "Direct",
13+
"requested": "[5.1.59, 5.1.59]",
14+
"resolved": "5.1.59",
15+
"contentHash": "/q/+sKyASsut6vz9f8V1/BQqdBt8H9WVurabW/WLvxq5I14+Ov8wDt7SnBOv4X4fwys88gfTHsCsX7ZX7Z0BcA=="
16+
},
17+
"nanoFramework.Runtime.Events": {
18+
"type": "Direct",
19+
"requested": "[1.11.1, 1.11.1]",
20+
"resolved": "1.11.1",
21+
"contentHash": "hHRPhNagq1T0oN9QJfPOqreuWUV42DJamT0f7GrPQvrOYcr9ne4YTZq8MIpudvKtSALs50iYqxJ+raOF2CiNsA=="
22+
},
23+
"nanoFramework.Runtime.Native": {
24+
"type": "Direct",
25+
"requested": "[1.5.4, 1.5.4]",
26+
"resolved": "1.5.4",
27+
"contentHash": "qfaOY1O5TOEw//MO4AOWRq5CdZXTfd3KnsGTNU2yw+IEYKiQLPkJhtF3ufF/S04xfXL556S2kOFG3/RZrwQ4Qw=="
28+
},
29+
"nanoFramework.System.Collections": {
30+
"type": "Direct",
31+
"requested": "[1.4.0, 1.4.0]",
32+
"resolved": "1.4.0",
33+
"contentHash": "/yFwxtCFzi+24NuyxcwlH1YyBGOxRX4oHGLwVmFbgbvOyx3ny/Mwyk2YjHTzmTSgUg9C2XxPF+EkXWwCOAkytw=="
34+
},
35+
"nanoFramework.System.IO.Streams": {
36+
"type": "Direct",
37+
"requested": "[1.1.27, 1.1.27]",
38+
"resolved": "1.1.27",
39+
"contentHash": "9ho/C/ZIQrBw51UnzLVbSc//kE1mDcgykGEZH8p+A5Q4R7JMVwdEKlNQXWr1VHEkGbv2wbyos6nRLqu2rdjpwA=="
40+
},
41+
"nanoFramework.System.Net": {
42+
"type": "Direct",
43+
"requested": "[1.10.38, 1.10.38]",
44+
"resolved": "1.10.38",
45+
"contentHash": "vMGSqPoJvvXmpJXir/QH7vgj3n3M/705IQtmWRo0a99HdVaXnc0iZmmRtLi8JKNGngwEDZ0ge4+ZBBqqtSsyrw=="
46+
},
47+
"nanoFramework.System.Text": {
48+
"type": "Direct",
49+
"requested": "[1.2.22, 1.2.22]",
50+
"resolved": "1.2.22",
51+
"contentHash": "vLvU0II3oJfajQ8MgNm8aCkaQ2JhjznzruwksOorbMJf86zLRbA5NUeg9X/KjbAE5pIalitUOqtNLKorYTbYGg=="
52+
},
53+
"nanoFramework.System.Threading": {
54+
"type": "Direct",
55+
"requested": "[1.1.8, 1.1.8]",
56+
"resolved": "1.1.8",
57+
"contentHash": "oES5GN3KHoDzifRNr06WM7P9NaQf+kDmIYkr1ETR2awmERHz4sRpECduGEatwyo1vMhMvZY/KoBcEpAyKNbDgQ=="
58+
},
59+
"nanoFramework.TestFramework": {
60+
"type": "Direct",
61+
"requested": "[2.0.60, 2.0.60]",
62+
"resolved": "2.0.60",
63+
"contentHash": "Sl+jB89CV3bAX4lmVoJYF/75a4EOjyfQSgaa6sPlUerUEI24y8KK4+s3EOv9UJFz6MGgJWJkQIas6D0Zv1jELw=="
64+
}
65+
}
66+
}
67+
}

azure-pipelines.yml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,8 @@ steps:
4949
- template: azure-pipelines-templates/class-lib-build.yml@templates
5050
parameters:
5151
sonarCloudProject: 'nanoframework_Azure.Devices'
52+
runUnitTests: true
53+
unitTestRunsettings: '$(System.DefaultWorkingDirectory)\.runsettings'
5254

5355
# step from template @ nf-tools repo
5456
# report error

nanoFramework.Azure.Devices.Client.sln

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,13 @@ Project("{11A8DD76-328B-46DF-9F39-F559912D0360}") = "TwinTests", "Tests\TwinTest
1818
EndProject
1919
Project("{11A8DD76-328B-46DF-9F39-F559912D0360}") = "CryptoTests", "Tests\CryptoTests\CryptoTests.nfproj", "{18856152-0A46-4B7F-BF38-82313AEB61F8}"
2020
EndProject
21+
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{29CB2BEC-F0F1-4B2B-A2A5-DCC9063F4BF0}"
22+
ProjectSection(SolutionItems) = preProject
23+
.runsettings = .runsettings
24+
EndProjectSection
25+
EndProject
26+
Project("{11A8DD76-328B-46DF-9F39-F559912D0360}") = "DeviceClientTests", "Tests\DeviceClientTests\DeviceClientTests.nfproj", "{557EF898-6CF2-4CBC-AE29-72F387FF0EE0}"
27+
EndProject
2128
Global
2229
GlobalSection(SolutionConfigurationPlatforms) = preSolution
2330
Debug|Any CPU = Debug|Any CPU
@@ -42,13 +49,20 @@ Global
4249
{18856152-0A46-4B7F-BF38-82313AEB61F8}.Release|Any CPU.ActiveCfg = Release|Any CPU
4350
{18856152-0A46-4B7F-BF38-82313AEB61F8}.Release|Any CPU.Build.0 = Release|Any CPU
4451
{18856152-0A46-4B7F-BF38-82313AEB61F8}.Release|Any CPU.Deploy.0 = Release|Any CPU
52+
{557EF898-6CF2-4CBC-AE29-72F387FF0EE0}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
53+
{557EF898-6CF2-4CBC-AE29-72F387FF0EE0}.Debug|Any CPU.Build.0 = Debug|Any CPU
54+
{557EF898-6CF2-4CBC-AE29-72F387FF0EE0}.Debug|Any CPU.Deploy.0 = Debug|Any CPU
55+
{557EF898-6CF2-4CBC-AE29-72F387FF0EE0}.Release|Any CPU.ActiveCfg = Release|Any CPU
56+
{557EF898-6CF2-4CBC-AE29-72F387FF0EE0}.Release|Any CPU.Build.0 = Release|Any CPU
57+
{557EF898-6CF2-4CBC-AE29-72F387FF0EE0}.Release|Any CPU.Deploy.0 = Release|Any CPU
4558
EndGlobalSection
4659
GlobalSection(SolutionProperties) = preSolution
4760
HideSolutionNode = FALSE
4861
EndGlobalSection
4962
GlobalSection(NestedProjects) = preSolution
5063
{50BED153-FF67-4207-ADB0-2651DDADC2A3} = {439F8827-FED8-45E0-9DA0-9DE277A29722}
5164
{18856152-0A46-4B7F-BF38-82313AEB61F8} = {439F8827-FED8-45E0-9DA0-9DE277A29722}
65+
{557EF898-6CF2-4CBC-AE29-72F387FF0EE0} = {439F8827-FED8-45E0-9DA0-9DE277A29722}
5266
EndGlobalSection
5367
GlobalSection(ExtensibilityGlobals) = postSolution
5468
SolutionGuid = {C967FC56-9F2D-40AD-8B89-52B96DFD776B}

0 commit comments

Comments
 (0)