Search code examples
c#json.netsystem.text.json

What is equivalent in JToken.DeepEquals in System.Text.Json?


I want to migrate my code from Newtonsoft Json.Net to Microsoft standard System.Text.Json. But I could not find an alternative for JToken.DeepEqual

Basically the code must compare two JSON in unit test. Reference JSON, and Result JSON. I used the mechanism in Newtonsoft to create two JObject and then compare them with JToken.DeepEqual. Here is the example code:

[TestMethod]
public void ExampleUnitTes()
{
    string resultJson = TestedUnit.TestedMethod();
    string referenceJson =
    @"
    {
      ...bla bla bla...
      ...some JSON Content...
      ...bla bla bla...
    }";

    JObject expected = ( JObject )JsonConvert.DeserializeObject( referenceJson );
    JObject result = ( JObject )JsonConvert.DeserializeObject( resultJson );
    Assert.IsTrue( JToken.DeepEquals( result, expected ) );
}

If I am correct the Newtonsoft JObject similar in System.Text.Json.JsonDocument, and I am able to create it, just I don't know how to compare the contents of it.

System.Text.Json.JsonDocument expectedDoc = System.Text.Json.JsonDocument.Parse( referenceJson );
System.Text.Json.JsonDocument resultDoc = System.Text.Json.JsonDocument.Parse( json );

Compare???( expectedDoc, resulDoc );

Of course, string compare is not a solution, because the format of the JSON doesn't matter and the order of the properties also doesn't matter.


Solution

  • UPDATE

    Since version 1.3.0 of my SystemTextJson.JsonDiffPatch NuGet package, you can use DeepEquals extension method to compare JsonDocument, JsonElement and JsonNode.

    Original Answer Below

    For the System.Text.Json.Nodes namespace introduced since .NET 6 release, there is currently a Github issue to discuss adding DeepEquals functionality to JsonNode.

    I rolled my own implementation of DeepEquals as part of my SystemTextJson.JsonDiffPatch NuGet package. By default, the extension compares raw text of JSON values, which is not what JToken.DeepEquals does. Semantic equality needs to be enabled as:

    var node1 = JsonNode.Parse("[1.0]");
    var node2 = JsonNode.Parse("[1]");
    
    // false
    bool equal = node1.DeepEquals(node2);
    // true
    bool semanticEqual = node1.DeepEquals(node2, JsonElementComparison.Semantic);