Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Inconsistency of System.Text.Json behavior between .NET Framework and .NET Core #30666

Closed
DenSmoke opened this issue Aug 23, 2019 · 5 comments
Closed

Comments

@DenSmoke
Copy link

JsonSerializer.Serialize works differently with double depending on target.
I wrote simple test to check System.Text.Json behavior comparing to Newtonsoft.Json

public struct TestStruct
{
    public TestStruct(double number)
    {
        DoubleField = number;
    }

    public double DoubleField { get; set; }
}

public class JsonTest
{

    [Theory]
    [InlineData(0.99999999999999)]
    [InlineData(0.999999999999999)]
    [InlineData(0.9999999999999999)]
    [InlineData(0.99999999999999999)]
    public void SystemTextJsonTest(double number)
    {
        var data = new TestStruct(number);
        var datastring = JsonSerializer.Serialize(data);
        var deserializedData = JsonSerializer.Deserialize<TestStruct>(datastring);
        Assert.Equal(data.DoubleField, deserializedData.DoubleField);
    }

    [Theory]
    [InlineData(0.99999999999999)]
    [InlineData(0.999999999999999)]
    [InlineData(0.9999999999999999)]
    [InlineData(0.99999999999999999)]
    public void NewtonsoftJsonTest(double number)
    {
        var data = new TestStruct(number);
        var dataString = Newtonsoft.Json.JsonConvert.SerializeObject(data);
        var deserializedData = Newtonsoft.Json.JsonConvert.DeserializeObject<TestStruct>(dataString);
        Assert.Equal(data.DoubleField, deserializedData.DoubleField);
    }
}

Results
image

For some reason JsonSerializer.Serialize rounds double when it exceeds 17 digits, but JsonConvert.Serialize doesn't.

I have ASP.NET Core Web API which is sending good JSON provided by System.Text.Json and this JSON is being deserialized on .NET Framework without problems so the problem is only with JsonSerializer.Serialize

@stephentoub
Copy link
Member

cc: @tannergooding

@Wraith2
Copy link
Contributor

Wraith2 commented Aug 23, 2019

@ahsonkhan
Copy link
Member

As I understand it, we use "G17" on full framework as part of this change dotnet/corefx#38322 since the defaults produce fewer strings that round-trip.

I believe the inconsistency you observed is expected due to the limitations in netfx (https://github.com/dotnet/corefx/issues/40406#issuecomment-522552006).

https://github.com/dotnet/corefx/blob/3d72b56b8e7d1e4e44262be6c45c2aac580bbbc4/src/System.Text.Json/src/System/Text/Json/Writer/Utf8JsonWriter.WriteValues.Double.cs#L98-L142

@ericstj
Copy link
Member

ericstj commented Aug 27, 2019

@tannergooding can you confirm this is by-design?

@tannergooding
Copy link
Member

Yes, this is by design; as per my explanation in the comment(s) @ahsonkhan linked to above.

@msftgits msftgits transferred this issue from dotnet/corefx Feb 1, 2020
@msftgits msftgits added this to the 3.0 milestone Feb 1, 2020
@tannergooding tannergooding removed their assignment May 26, 2020
@ghost ghost locked as resolved and limited conversation to collaborators Dec 12, 2020
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

7 participants