Repository navigation
Open
Labels
api-suggestionEarly API idea and discussion, it is NOT ready for implementationEarly API idea and discussion, it is NOT ready for implementationarea-System.Text.JsonwishlistIssue we would like to prioritize, but we can't commit we will get to it yetIssue we would like to prioritize, but we can't commit we will get to it yet
Milestone
Description
Background and motivation
Currently System.Text.Json has no support for serializing BigInteger values. This is a proposal for serializing BigInteger values as arbitrarily sized JSON numbers.
API Proposal
namespace System.Text.Json
{
public ref partial struct Utf8JsonReader
{
+ public BigInteger GetBigInteger();
+ public bool TryGetBigInteger(out BigInteger value);
}
public sealed partial class Utf8JsonWriter
{
+ public void WriteNumber(JsonEncodedText propertyName, BigInteger value);
+ public void WriteNumber(string propertyName, BigInteger value);
+ public void WriteNumber(ReadOnlySpan<char> propertyName, BigInteger value);
+ public void WriteNumber(ReadOnlySpan<byte> utf8PropertyName, BigInteger value);
+ public void WriteNumberValue(BigInteger value);
}
public readonly partial struct JsonElement
{
+ public BigInteger GetBigInteger();
+ public bool TryGetBigInteger(out BigInteger value)
}
}
namespace System.Text.Json.Node
{
public abstract partial class JsonNode
{
+ public static explicit operator BigInteger(JsonNode value);
+ public static explicit operator BigInteger?(JsonNode? value);
+ public static implicit operator JsonNode(BigInteger value);
+ public static implicit operator JsonNode?(BigInteger? value);
}
}
namespace System.Text.Json.Serialization.Metadata
{
public static partial class JsonMetadataServices
{
+ public static JsonConverter<BigInteger> BigIntegerConverter { get; }
}
}API Usage
JsonSerializer.Serialize((BigInteger)42);
// Current JSON: {"IsPowerOfTwo":false,"IsZero":false,"IsOne":false,"IsEven":true,"Sign":1}
// New JSON: 42Alternative Designs
No response
Risks
No response
Reacted by Stefan, Martin Costello, John, Ben Meredith, akintos, elgonzo, Paulus Pärssinen, timaiv, Oualid Boutemine, Arad Alvand and 9 more
Metadata
Metadata
Assignees
Labels
api-suggestionEarly API idea and discussion, it is NOT ready for implementationEarly API idea and discussion, it is NOT ready for implementationarea-System.Text.JsonwishlistIssue we would like to prioritize, but we can't commit we will get to it yetIssue we would like to prioritize, but we can't commit we will get to it yet
Activity
eiriktsarpalis commentedon Oct 22, 2021
From @Tornhoof in #60763 (comment)
eiriktsarpalis commentedon Oct 22, 2021
From @tannergooding in #60763 (comment)
Tornhoof commentedon Oct 22, 2021
I looked at other JSON implementations, apparently most simply write it as a number.
There is even https://www.npmjs.com/package/json-bigint, which bypasses the bigint in javascript problem.
So i withdraw my objections.
jkotas commentedon Oct 22, 2021
Is this going to make BigInteger rooted for trimming in any use of
System.Text.Json?eiriktsarpalis commentedon Oct 23, 2021
Yes.
jkotas commentedon Oct 23, 2021
It means that this feature would introduce noticeable size regression for minimal Blazor apps where we care about size a lot. I doubt it would be acceptable. Features like this one have to be designed as opt-in.
cc @marek-safar
eiriktsarpalis commentedon Oct 25, 2021
Definitely, and this is really a concern with any type we propose to support OOTB (e.g. #53539). I don't think this should be preventing us from adding OOTB support for new types altogether, but we should definitely be weighing in the value of each proposal on a case-by-case basis.
I'm slightly concerned about the UX of needing to opt in to a valid serialization of a type we claim to support OOTB. Not supporting it at all is likely preferable (though I would need to check if a custom converter workaround is currently possible: it's not clear to me if
Utf8JsonReadercurrently supports reading arbitrarily large JSON numbers).stephentoub commentedon Oct 25, 2021
I agree we need to come up with an alternate approach that enables us to add in such support without rooting everything. The current path isn't sustainable.
1 remaining item
layomia commentedon Oct 25, 2021
Seems like a hard stance to take for right now as the feature stabilizes. However, this is the latest thinking based on 6.0 discussions: that the reflection serializer would be characterized as unfriendly for trimming by-design, and that folks that care about size should use the generator. cc @eerhardt
What's the motivation for the API proposal for .NET 7.0? Custom user converters can handle
BigInteger. If best perf is required, we could pursue #54410 (non-allocating view on string props when reading) and leverage the new Utf8JsonWriter.WriteRawValue methods.eiriktsarpalis commentedon Oct 25, 2021
No particular motivation. I added it to the 7.0.0 milestone so that it can be considered during our planning. I should add this is merely transcribing the ask in #60763 into an API proposal.
eiriktsarpalis commentedon Oct 25, 2021
Note that the particular use case would require extending the feature to also include JSON numbers.
jkotas commentedon Oct 25, 2021
I do not think that the reflection-based serializers are a sustainable choice for the core platform. Reflection-based serializers come with too many issues (compatibility and performance in particular). Case in point: All older reflection-based serializers in the core platform are in sustained engineering mode, they are impossible to evolve.
eiriktsarpalis commentedon Feb 10, 2023
I'd like to revisit this concern. Nowadays, any trimmed application using the source generator sees the bulk of built-in converters being trimmed and components are kept on a pay-for-play basis. I don't think this should be a blocker for us introducing built-in support for types, asssuming they are sufficiently popular.
cc @eerhardt
eerhardt commentedon Feb 13, 2023
Note this is true for apps the only support the source generator and disable/disallow reflection fallback for Json serialization. However, Blazor WASM and Maui apps don't fall into that category. Those apps only trim the base libraries, but not the user code. Both app models still use reflection based serialization.
eiriktsarpalis commentedon Feb 13, 2023
Interesting, thanks.
eiriktsarpalis commentedon Jun 24, 2023
Closing in favor of #87994
eiriktsarpalis commentedon Jun 27, 2023
Reopening since
BigIntegerwas cut from #87994. When implementing we might want to consider implementing a max digit threshold when deserializing. Related to #55121, which however only applies toBigIntegerimplementations post .NET 7.