Skip to content

Commit

Permalink
Implement Unit deserialization; Add the tests
Browse files Browse the repository at this point in the history
  • Loading branch information
andreise committed May 27, 2024
1 parent 3787d56 commit 1943f97
Show file tree
Hide file tree
Showing 13 changed files with 351 additions and 7 deletions.
8 changes: 4 additions & 4 deletions .github/workflows/dotnet.yml
Original file line number Diff line number Diff line change
Expand Up @@ -49,11 +49,11 @@ jobs:
- name: Test Unit.Tests.Old
run: dotnet test ./src/*/*/Unit.Tests.Old.csproj --no-restore -c Release

# - name: Restore Unit.Tests
# run: dotnet restore ./src/*/*/Unit.Tests.csproj
- name: Restore Unit.Tests
run: dotnet restore ./src/*/*/Unit.Tests.csproj

# - name: Test Unit.Tests
# run: dotnet test ./src/*/*/Unit.Tests.csproj --no-restore -c Release
- name: Test Unit.Tests
run: dotnet test ./src/*/*/Unit.Tests.csproj --no-restore -c Release

# Push

Expand Down
1 change: 1 addition & 0 deletions src/core-unit/Unit.Tests.Old/GlobalUsings.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
global using NUnit.Framework;
2 changes: 1 addition & 1 deletion src/core-unit/Unit.Tests.Old/Unit.Tests.Old.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.9.0" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.10.0" />
<PackageReference Include="Moq" Version="4.20.70" />
<PackageReference Include="NUnit" Version="4.1.0" />
<PackageReference Include="NUnit.Analyzers" Version="4.2.0">
Expand Down
1 change: 1 addition & 0 deletions src/core-unit/Unit.Tests/GlobalUsings.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
global using Xunit;
39 changes: 39 additions & 0 deletions src/core-unit/Unit.Tests/Unit.Tests.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<TargetFrameworks>net8.0</TargetFrameworks>
<LangVersion>latest</LangVersion>
<ImplicitUsings>disable</ImplicitUsings>
<Nullable>enable</Nullable>
<InvariantGlobalization>true</InvariantGlobalization>
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<IsPackable>false</IsPackable>
<IsTestProject>true</IsTestProject>
<Authors>Andrei Sergeev, Pavel Moskovoy</Authors>
<Copyright>Copyright © 2020-2024 Andrei Sergeev, Pavel Moskovoy</Copyright>
<RootNamespace>PrimeFuncPack.Core.Tests</RootNamespace>
<AssemblyName>PrimeFuncPack.Core.Unit.Tests</AssemblyName>
</PropertyGroup>

<PropertyGroup>
<NoWarn>$(NoWarn);xUnit1044</NoWarn>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="coverlet.collector" Version="6.0.2">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.10.0" />
<PackageReference Include="xunit" Version="2.8.1" />
<PackageReference Include="xunit.runner.visualstudio" Version="2.8.1">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
</ItemGroup>

<ItemGroup>
<ProjectReference Include="..\Unit\Unit.csproj" />
</ItemGroup>

</Project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
using System;
using System.Text.Json;
using System.Text.Json.Nodes;

namespace PrimeFuncPack.Core.Tests;

partial class UnitSerializationTests
{
[Theory]
[MemberData(nameof(DeserializeArrayToUnit_ExpectNoException_Cases))]
public static void DeserializeArrayToUnitFromString_ExpectNoException(
JsonArray source,
JsonSerializerOptions? options)
{
var sourceString = JsonSerializer.Serialize(source);
_ = JsonSerializer.Deserialize<Unit>(sourceString, options);
}

[Theory]
[MemberData(nameof(DeserializeArrayToUnit_ExpectNoException_Cases))]
public static void DeserializeArrayToUnitFromObject_ExpectNoException(
JsonArray source,
JsonSerializerOptions? options)
{
_ = JsonSerializer.Deserialize<Unit>(source, options);
}

public static TheoryData<JsonArray, JsonSerializerOptions?> DeserializeArrayToUnit_ExpectNoException_Cases
{
get
{
var arrays = new JsonArray[]
{
[],
new(new JsonArray(null, true, false, -1, 0, 1.1m, 1.2, "2"))
};

var result = new TheoryData<JsonArray, JsonSerializerOptions?>();

foreach (var array in arrays)
{
foreach (var options in BuildJsonSerializerOptionsCollection())
{
result.Add(array, options);
}
}

return result;
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
using System;
using System.Text.Json;
using System.Text.Json.Nodes;

namespace PrimeFuncPack.Core.Tests;

partial class UnitSerializationTests
{
[Theory]
[MemberData(nameof(DeserializeNonEmptyObjectToUnit_ExpectNoException_Cases))]
public static void DeserializeNonEmptyObjectToUnitFromString_ExpectNoException(
JsonObject source,
JsonSerializerOptions? options)
{
var sourceString = JsonSerializer.Serialize(source);
_ = JsonSerializer.Deserialize<Unit>(sourceString, options);
}

[Theory]
[MemberData(nameof(DeserializeNonEmptyObjectToUnit_ExpectNoException_Cases))]
public static void DeserializeNonEmptyObjectToUnitFromObject_ExpectNoException(
JsonObject source,
JsonSerializerOptions? options)
{
_ = JsonSerializer.Deserialize<Unit>(source, options);
}

public static TheoryData<JsonObject, JsonSerializerOptions?> DeserializeNonEmptyObjectToUnit_ExpectNoException_Cases
{
get
{
var objects = new JsonObject[]
{
new()
{
["id"] = "0AFB2897-BA58-4E10-A083-4C33341B6238"
},
new()
{
["id"] = "0AFB2897-BA58-4E10-A083-4C33341B6238",
["body"] = new JsonObject
{
["foo"] = 1,
["bar"] = "2",
["baz"] = new JsonArray(null, true, 1, "2"),
},
["qux"] = new JsonArray(false, -1, 0, 1.1m, 1.2, "3"),
["quux"] = new JsonArray(),
["corge"] = -1.1m,
["grault"] = -1.2,
["garply"] = true,
["waldo"] = false,
["fred"] = null,
}
};

var result = new TheoryData<JsonObject, JsonSerializerOptions?>();

foreach (var obj in objects)
{
foreach (var options in BuildJsonSerializerOptionsCollection())
{
result.Add(obj, options);
}
}

return result;
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
using System;
using System.Text.Json;
using System.Text.Json.Nodes;

namespace PrimeFuncPack.Core.Tests;

partial class UnitSerializationTests
{
[Theory]
[MemberData(nameof(JsonSerializerOptionsCases))]
public static void DeserializeNullToUnitFromString_ExpectNoException(JsonSerializerOptions? options)
{
var source = JsonSerializer.Serialize<JsonNode?>(null);
_ = JsonSerializer.Deserialize<Unit>(source, options);
}

[Theory]
[MemberData(nameof(JsonSerializerOptionsCases))]
public static void DeserializeNullToUnitFromNode_ExpectNoException(JsonSerializerOptions? options)
{
JsonNode? source = null;
_ = JsonSerializer.Deserialize<Unit>(source, options);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
using System;
using System.Text.Json;
using System.Text.Json.Nodes;

namespace PrimeFuncPack.Core.Tests;

partial class UnitSerializationTests
{
[Theory]
[MemberData(nameof(DeserializeSimpleValueToUnit_ExpectNoException_Cases))]
public static void DeserializeSimpleValueToUnitFromString_ExpectNoException(
JsonNode source,
JsonSerializerOptions? options)
{
var sourceString = JsonSerializer.Serialize(source);
_ = JsonSerializer.Deserialize<Unit>(sourceString, options);
}

[Theory]
[MemberData(nameof(DeserializeSimpleValueToUnit_ExpectNoException_Cases))]
public static void DeserializeSimpleValueToUnitFromObject_ExpectNoException(
JsonNode source,
JsonSerializerOptions? options)
{
_ = JsonSerializer.Deserialize<Unit>(source, options);
}

public static TheoryData<JsonNode, JsonSerializerOptions?> DeserializeSimpleValueToUnit_ExpectNoException_Cases
{
get
{
var values = new JsonNode[]
{
true,
false,

int.MinValue,
-1,
0,
1.1m,
1.2,
int.MaxValue,

double.MinValue,
double.MaxValue,

"",
"1",
"0AFB2897-BA58-4E10-A083-4C33341B6238"
};

var result = new TheoryData<JsonNode, JsonSerializerOptions?>();

foreach (var value in values)
{
foreach (var options in BuildJsonSerializerOptionsCollection())
{
result.Add(value, options);
}
}

return result;
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
using System;
using System.Text.Json;
using System.Text.Json.Nodes;

namespace PrimeFuncPack.Core.Tests;

partial class UnitSerializationTests
{
[Theory]
[MemberData(nameof(JsonSerializerOptionsCases))]
public static void DeserializeUnitFromString_ExpectNoException(JsonSerializerOptions? options)
{
var source = JsonSerializer.Serialize(new JsonObject()); // default options expected
_ = JsonSerializer.Deserialize<Unit>(source, options);
}

[Theory]
[MemberData(nameof(JsonSerializerOptionsCases))]
public static void DeserializeUnitFromNode_ExpectNoException(JsonSerializerOptions? options)
{
var source = new JsonObject();
_ = JsonSerializer.Deserialize<Unit>(source, options);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
using System;
using System.Text.Json;
using System.Text.Json.Nodes;

namespace PrimeFuncPack.Core.Tests;

partial class UnitSerializationTests
{
[Theory]
[MemberData(nameof(JsonSerializerOptionsCases))]
public static void SerializeUnitToString_ExpectEmptyJsonObject(JsonSerializerOptions? options)
{
var actual = JsonSerializer.Serialize(default(Unit), options);
var expected = JsonSerializer.Serialize(new JsonObject()); // default options expected
Assert.Equal(expected, actual);
}

[Theory]
[MemberData(nameof(JsonSerializerOptionsCases))]
public static void SerializeUnitToNode_ExpectEmptyJsonObject(JsonSerializerOptions? options)
{
var actual = JsonSerializer.SerializeToNode(default(Unit), options);
var expected = new JsonObject();
Assert.Equal(expected, actual);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
using System.Collections.Generic;
using System.Linq;
using System.Text.Json;

namespace PrimeFuncPack.Core.Tests;

public static partial class UnitSerializationTests
{
public static TheoryData<JsonSerializerOptions?> JsonSerializerOptionsCases
=>
new(BuildJsonSerializerOptionsCollection().ToArray());

private static IEnumerable<JsonSerializerOptions?> BuildJsonSerializerOptionsCollection()
{
yield return null;
yield return JsonSerializerOptions.Default;
yield return new(JsonSerializerDefaults.General);
yield return new(JsonSerializerDefaults.Web);
}
}
27 changes: 25 additions & 2 deletions src/core-unit/Unit/UnitJsonConverter/UnitJsonConverter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,31 @@ namespace System;
internal sealed class UnitJsonConverter : JsonConverter<Unit>
{
public override Unit Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
=>
default;
{
var tokenType = reader.TokenType;
Debug.Assert(tokenType is not JsonTokenType.None);

switch (tokenType)
{
case JsonTokenType.StartObject:
case JsonTokenType.StartArray:
reader.Skip();
Debug.Assert(
tokenType is JsonTokenType.StartObject && reader.TokenType is JsonTokenType.EndObject ||
tokenType is JsonTokenType.StartArray && reader.TokenType is JsonTokenType.EndArray);
return default;

case JsonTokenType.String:
case JsonTokenType.Number:
case JsonTokenType.True:
case JsonTokenType.False:
case JsonTokenType.Null:
return default;

default:
throw new JsonException($"An unexpected JSON token type ({tokenType}).");
};
}

public override void Write(Utf8JsonWriter writer, Unit value, JsonSerializerOptions options)
{
Expand Down

0 comments on commit 1943f97

Please sign in to comment.