Como migrar do Newtonsoft.Json para o System.Text.JsonHow to migrate from Newtonsoft.Json to System.Text.Json
Este artigo mostra como migrar do Newtonsoft.Json para o System.Text.Json .This article shows how to migrate from Newtonsoft.Json to System.Text.Json.
O System.Text.Json
namespace fornece a funcionalidade para serializar e desserializar de JavaScript Object Notation (JSON).The System.Text.Json
namespace provides functionality for serializing to and deserializing from JavaScript Object Notation (JSON). A System.Text.Json
biblioteca está incluída no tempo de execução para .net Core 3,1 e versões posteriores.The System.Text.Json
library is included in the runtime for .NET Core 3.1 and later versions. Para outras estruturas de destino, instale o System.Text.Json pacote NuGet.For other target frameworks, install the System.Text.Json NuGet package. O pacote dá suporte a:The package supports:
- .NET Standard 2,0 e versões posteriores.NET Standard 2.0 and later versions
- .NET Framework 4.7.2 e versões posteriores.NET Framework 4.7.2 and later versions
- .NET Core 2,0, 2,1 e 2,2.NET Core 2.0, 2.1, and 2.2
System.Text.Json
concentra-se principalmente em desempenho, segurança e conformidade de padrões.System.Text.Json
focuses primarily on performance, security, and standards compliance. Ele tem algumas diferenças importantes no comportamento padrão e não tem como objetivo ter paridade de recursos com o Newtonsoft.Json
.It has some key differences in default behavior and doesn't aim to have feature parity with Newtonsoft.Json
. Para alguns cenários, o System.Text.Json
não tem funcionalidade interna, mas há soluções alternativas recomendadas.For some scenarios, System.Text.Json
has no built-in functionality, but there are recommended workarounds. Para outros cenários, as soluções alternativas são impraticável.For other scenarios, workarounds are impractical. Se seu aplicativo depende de um recurso ausente, considere o arquivamento de um problema para descobrir se o suporte para seu cenário pode ser adicionado.If your application depends on a missing feature, consider filing an issue to find out if support for your scenario can be added.
A maior parte deste artigo é sobre como usar a JsonSerializer API, mas também inclui orientação sobre como usar o JsonDocument (que representa os tipos modelo de objeto do documento ou dom), Utf8JsonReader e Utf8JsonWriter .Most of this article is about how to use the JsonSerializer API, but it also includes guidance on how to use the JsonDocument (which represents the Document Object Model or DOM), Utf8JsonReader, and Utf8JsonWriter types.
No Visual Basic, não é possível usar Utf8JsonReader o, o que também significa que você não pode escrever conversores personalizados.In Visual Basic, you can't use Utf8JsonReader, which also means you can't write custom converters. A maioria das soluções alternativas apresentadas aqui requer que você escreva conversores personalizados.Most of the workarounds presented here require that you write custom converters. Você pode escrever um conversor personalizado em C# e registrá-lo em um projeto Visual Basic.You can write a custom converter in C# and register it in a Visual Basic project. Para obter mais informações, consulte suporte a Visual Basic.For more information, see Visual Basic support.
Tabela de diferenças entre Newtonsoft.Json e System.Text.JsonTable of differences between Newtonsoft.Json and System.Text.Json
A tabela a seguir lista os Newtonsoft.Json
recursos e System.Text.Json
equivalentes.The following table lists Newtonsoft.Json
features and System.Text.Json
equivalents. Os equivalentes se enquadram nas seguintes categorias:The equivalents fall into the following categories:
- Com suporte pela funcionalidade interna.Supported by built-in functionality. Obter comportamento semelhante do
System.Text.Json
pode exigir o uso de um atributo ou uma opção global.Getting similar behavior fromSystem.Text.Json
may require the use of an attribute or global option. - Sem suporte, a solução alternativa é possível.Not supported, workaround is possible. As soluções alternativas são conversores personalizados, que podem não fornecer paridade completa com
Newtonsoft.Json
funcionalidade.The workarounds are custom converters, which may not provide complete parity withNewtonsoft.Json
functionality. Para alguns deles, o código de exemplo é fornecido como exemplos.For some of these, sample code is provided as examples. Se você depender dessesNewtonsoft.Json
recursos, a migração exigirá modificações em seus modelos de objeto .net ou em outras alterações de código.If you rely on theseNewtonsoft.Json
features, migration will require modifications to your .NET object models or other code changes. - Sem suporte, a solução alternativa não é prática ou possível.Not supported, workaround is not practical or possible. Se você depender desses
Newtonsoft.Json
recursos, a migração não será possível sem alterações significativas.If you rely on theseNewtonsoft.Json
features, migration will not be possible without significant changes.
Recurso do Newtonsoft.JsonNewtonsoft.Json feature | System.Text.Json equivalenteSystem.Text.Json equivalent | |
---|---|---|
Desserialização não diferencia maiúsculas de minúsculas por padrãoCase-insensitive deserialization by default | configuração global do ✔️ PropertyNameCaseInsensitive✔️ PropertyNameCaseInsensitive global setting | |
Nomes de Propriedade do camel caseCamel-case property names | configuração global do ✔️ PropertyNamingPolicy✔️ PropertyNamingPolicy global setting | |
Escape de caractere mínimoMinimal character escaping | ✔️ escape de caractere estrito, configurável✔️ Strict character escaping, configurable | |
NullValueHandling.Ignore configuração globalNullValueHandling.Ignore global setting |
✔️ opção global DefaultIgnoreCondition✔️ DefaultIgnoreCondition global option | Ignorar condicionalmente uma propriedadeConditionally ignore a property |
Permitir comentáriosAllow comments | configuração global do ✔️ ReadCommentHandling✔️ ReadCommentHandling global setting | |
Permitir vírgulas à direitaAllow trailing commas | configuração global do ✔️ AllowTrailingCommas✔️ AllowTrailingCommas global setting | |
Registro do conversor personalizadoCustom converter registration | ✔️ ordem de precedência difere✔️ Order of precedence differs | |
Sem profundidade máxima por padrãoNo maximum depth by default | ✔️ profundidade máxima padrão 64, configurável✔️ Default maximum depth 64, configurable | |
PreserveReferencesHandling configuração globalPreserveReferencesHandling global setting |
configuração global do ✔️ ReferenceHandling✔️ ReferenceHandling global setting | |
Serializar ou desserializar números entre aspasSerialize or deserialize numbers in quotes | ✔️ configuração global do NumberHandling, atributo [JsonNumberHandling]✔️ NumberHandling global setting, [JsonNumberHandling] attribute | |
Desserializar para classes e structs imutáveisDeserialize to immutable classes and structs | ✔️ JsonConstructor, C# 9 registros✔️ JsonConstructor, C# 9 Records | |
Suporte para camposSupport for fields | ✔️ configuração global do IncludeFields, atributo [JsonInclude]✔️ IncludeFields global setting, [JsonInclude] attribute | |
DefaultValueHandling configuração globalDefaultValueHandling global setting |
configuração global do ✔️ DefaultIgnoreCondition✔️ DefaultIgnoreCondition global setting | |
NullValueHandling configuração em [JsonProperty] NullValueHandling setting on [JsonProperty] |
✔️ atributo JsonIgnore✔️ JsonIgnore attribute | |
DefaultValueHandling configuração em [JsonProperty] DefaultValueHandling setting on [JsonProperty] |
✔️ atributo JsonIgnore✔️ JsonIgnore attribute | |
Desserializar Dictionary com chave não cadeia de caracteresDeserialize Dictionary with non-string key |
✔️ com suporte✔️ Supported | |
Suporte para setters e getters de propriedade não públicaSupport for non-public property setters and getters | ✔️ atributo JsonInclude✔️ JsonInclude attribute | |
Atributo [JsonConstructor] [JsonConstructor] attribute |
atributo ✔️ [JsonConstructor]✔️ [JsonConstructor] attribute | |
Suporte para uma ampla variedade de tiposSupport for a broad range of types | ⚠️Alguns tipos exigem conversores personalizados⚠️ Some types require custom converters | |
Serialização polimórficaPolymorphic serialization | ⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample | |
Desserialização polimórficaPolymorphic deserialization | ⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample | |
Desserializar tipo inferido para object PropriedadesDeserialize inferred type to object properties |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample | |
Desserializar null literal JSON para tipos de valores não anuláveisDeserialize JSON null literal to non-nullable value types |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample | |
Required Configurando no [JsonProperty] atributoRequired setting on [JsonProperty] attribute |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample | |
DefaultContractResolver para ignorar PropriedadesDefaultContractResolver to ignore properties |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample | |
DateTimeZoneHandling , DateFormatString configuraçõesDateTimeZoneHandling , DateFormatString settings |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample | |
Retornos de chamadaCallbacks | ⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample | |
Método JsonConvert.PopulateObject JsonConvert.PopulateObject method |
⚠️Sem suporte, solução alternativa⚠️ Not supported, workaround | |
ObjectCreationHandling configuração globalObjectCreationHandling global setting |
⚠️Sem suporte, solução alternativa⚠️ Not supported, workaround | |
Adicionar a coleções sem settersAdd to collections without setters | ⚠️Sem suporte, solução alternativa⚠️ Not supported, workaround | |
ReferenceLoopHandling configuração globalReferenceLoopHandling global setting |
❌ Sem suporte❌ Not supported | |
Suporte para System.Runtime.Serialization atributosSupport for System.Runtime.Serialization attributes |
❌ Sem suporte❌ Not supported | |
MissingMemberHandling configuração globalMissingMemberHandling global setting |
❌ Sem suporte❌ Not supported | |
Permitir nomes de propriedade sem aspasAllow property names without quotes | ❌ Sem suporte❌ Not supported | |
Permitir aspas simples em vez de valores de cadeia de caracteresAllow single quotes around string values | ❌ Sem suporte❌ Not supported | |
Permitir valores JSON que não são de cadeia de caracteres para propriedades de cadeia de caracteresAllow non-string JSON values for string properties | ❌ Sem suporte❌ Not supported | |
TypeNameHandling.All configuração globalTypeNameHandling.All global setting |
❌ Sem suporte❌ Not supported |
Recurso do Newtonsoft.JsonNewtonsoft.Json feature | System.Text.Json equivalenteSystem.Text.Json equivalent |
---|---|
Desserialização não diferencia maiúsculas de minúsculas por padrãoCase-insensitive deserialization by default | configuração global do ✔️ PropertyNameCaseInsensitive✔️ PropertyNameCaseInsensitive global setting |
Nomes de Propriedade do camel caseCamel-case property names | configuração global do ✔️ PropertyNamingPolicy✔️ PropertyNamingPolicy global setting |
Escape de caractere mínimoMinimal character escaping | ✔️ escape de caractere estrito, configurável✔️ Strict character escaping, configurable |
NullValueHandling.Ignore configuração globalNullValueHandling.Ignore global setting |
✔️ opção global IgnoreNullValues✔️ IgnoreNullValues global option |
Permitir comentáriosAllow comments | configuração global do ✔️ ReadCommentHandling✔️ ReadCommentHandling global setting |
Permitir vírgulas à direitaAllow trailing commas | configuração global do ✔️ AllowTrailingCommas✔️ AllowTrailingCommas global setting |
Registro do conversor personalizadoCustom converter registration | ✔️ ordem de precedência difere✔️ Order of precedence differs |
Sem profundidade máxima por padrãoNo maximum depth by default | ✔️ profundidade máxima padrão 64, configurável✔️ Default maximum depth 64, configurable |
Suporte para uma ampla variedade de tiposSupport for a broad range of types | ⚠️Alguns tipos exigem conversores personalizados⚠️ Some types require custom converters |
Desserializar cadeias de caracteres como númerosDeserialize strings as numbers | ⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
Desserializar Dictionary com chave não cadeia de caracteresDeserialize Dictionary with non-string key |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
Serialização polimórficaPolymorphic serialization | ⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
Desserialização polimórficaPolymorphic deserialization | ⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
Desserializar tipo inferido para object PropriedadesDeserialize inferred type to object properties |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
Desserializar null literal JSON para tipos de valores não anuláveisDeserialize JSON null literal to non-nullable value types |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
Desserializar para classes e structs imutáveisDeserialize to immutable classes and structs | ⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
Atributo [JsonConstructor] [JsonConstructor] attribute |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
Required Configurando no [JsonProperty] atributoRequired setting on [JsonProperty] attribute |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
NullValueHandling Configurando no [JsonProperty] atributoNullValueHandling setting on [JsonProperty] attribute |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
DefaultValueHandling Configurando no [JsonProperty] atributoDefaultValueHandling setting on [JsonProperty] attribute |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
DefaultValueHandling configuração globalDefaultValueHandling global setting |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
DefaultContractResolver para ignorar PropriedadesDefaultContractResolver to ignore properties |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
DateTimeZoneHandling , DateFormatString configuraçõesDateTimeZoneHandling , DateFormatString settings |
⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
Retornos de chamadaCallbacks | ⚠️Sem suporte, solução alternativa, exemplo⚠️ Not supported, workaround, sample |
Suporte para campos públicos e não públicosSupport for public and non-public fields | ⚠️Sem suporte, solução alternativa⚠️ Not supported, workaround |
Suporte para setters e getters de propriedade não públicaSupport for non-public property setters and getters | ⚠️Sem suporte, solução alternativa⚠️ Not supported, workaround |
Método JsonConvert.PopulateObject JsonConvert.PopulateObject method |
⚠️Sem suporte, solução alternativa⚠️ Not supported, workaround |
ObjectCreationHandling configuração globalObjectCreationHandling global setting |
⚠️Sem suporte, solução alternativa⚠️ Not supported, workaround |
Adicionar a coleções sem settersAdd to collections without setters | ⚠️Sem suporte, solução alternativa⚠️ Not supported, workaround |
PreserveReferencesHandling configuração globalPreserveReferencesHandling global setting |
❌ Sem suporte❌ Not supported |
ReferenceLoopHandling configuração globalReferenceLoopHandling global setting |
❌ Sem suporte❌ Not supported |
Suporte para System.Runtime.Serialization atributosSupport for System.Runtime.Serialization attributes |
❌ Sem suporte❌ Not supported |
MissingMemberHandling configuração globalMissingMemberHandling global setting |
❌ Sem suporte❌ Not supported |
Permitir nomes de propriedade sem aspasAllow property names without quotes | ❌ Sem suporte❌ Not supported |
Permitir aspas simples em vez de valores de cadeia de caracteresAllow single quotes around string values | ❌ Sem suporte❌ Not supported |
Permitir valores JSON que não são de cadeia de caracteres para propriedades de cadeia de caracteresAllow non-string JSON values for string properties | ❌ Sem suporte❌ Not supported |
TypeNameHandling.All configuração globalTypeNameHandling.All global setting |
❌ Sem suporte❌ Not supported |
Esta não é uma lista completa de Newtonsoft.Json
recursos.This is not an exhaustive list of Newtonsoft.Json
features. A lista inclui muitos dos cenários que foram solicitados em problemas do GitHub ou postagens do StackOverflow .The list includes many of the scenarios that have been requested in GitHub issues or StackOverflow posts. Se você implementar uma solução alternativa para um dos cenários listados aqui que não tem um código de exemplo, e se você quiser compartilhar sua solução, selecione esta página na seção de comentários na parte inferior desta página.If you implement a workaround for one of the scenarios listed here that doesn't currently have sample code, and if you want to share your solution, select This page in the Feedback section at the bottom of this page. Isso cria um problema no repositório GitHub da documentação e o lista na seção de comentários nesta página também.That creates an issue in this documentation's GitHub repo and lists it in the Feedback section on this page too.
Diferenças no comportamento padrão de JsonSerializer em comparação com Newtonsoft.JsonDifferences in default JsonSerializer behavior compared to Newtonsoft.Json
System.Text.Json é estrito por padrão e evita qualquer adivinhação ou interpretação em nome do chamador, enfatizando o comportamento determinístico.System.Text.Json is strict by default and avoids any guessing or interpretation on the caller's behalf, emphasizing deterministic behavior. A biblioteca foi projetada intencionalmente dessa forma para desempenho e segurança.The library is intentionally designed this way for performance and security. Newtonsoft.Json
é flexível por padrão.Newtonsoft.Json
is flexible by default. Essa diferença fundamental no design está por trás de muitas das diferenças específicas a seguir no comportamento padrão.This fundamental difference in design is behind many of the following specific differences in default behavior.
Desserialização não diferencia maiúsculas de minúsculasCase-insensitive deserialization
Durante a desserialização, Newtonsoft.Json
o nome da propriedade que não diferencia maiúsculas de minúsculas corresponde por padrão.During deserialization, Newtonsoft.Json
does case-insensitive property name matching by default. O System.Text.Json padrão diferencia maiúsculas de minúsculas, o que proporciona melhor desempenho, pois está fazendo uma correspondência exata.The System.Text.Json default is case-sensitive, which gives better performance since it's doing an exact match. Para obter informações sobre como fazer a correspondência que não diferencia maiúsculas de minúsculas, consulte correspondência de propriedadeque não diferencia maiúsculas de minúsculas.For information about how to do case-insensitive matching, see Case-insensitive property matching.
Se você estiver usando System.Text.Json
indiretamente usando ASP.NET Core, não precisará fazer nada para obter o comportamento como Newtonsoft.Json
.If you're using System.Text.Json
indirectly by using ASP.NET Core, you don't need to do anything to get behavior like Newtonsoft.Json
. ASP.NET Core especifica as configurações para os nomes de Propriedade do Camel case e a correspondência que não diferencia maiúsculas de minúsculas quando ela usa System.Text.Json
.ASP.NET Core specifies the settings for camel-casing property names and case-insensitive matching when it uses System.Text.Json
.
O ASP.NET Core também permite a desserialização de números entre aspas por padrão.ASP.NET Core also enables deserializing quoted numbers by default.
Escape de caractere mínimoMinimal character escaping
Durante a serialização, Newtonsoft.Json
é relativamente permissivo de permitir caracteres sem escape.During serialization, Newtonsoft.Json
is relatively permissive about letting characters through without escaping them. Ou seja, ele não os substitui por \uxxxx
Where xxxx
é o ponto de código do caractere.That is, it doesn't replace them with \uxxxx
where xxxx
is the character's code point. Em que ele faz escape, ele faz isso emitindo um \
antes do caractere (por exemplo, "
se torna \"
).Where it does escape them, it does so by emitting a \
before the character (for example, "
becomes \"
). System.Text.Json escapa mais caracteres por padrão para fornecer proteções de defesa profunda contra XSS (script entre sites) ou ataques de divulgação de informações e faz isso usando a sequência de seis caracteres.System.Text.Json escapes more characters by default to provide defense-in-depth protections against cross-site scripting (XSS) or information-disclosure attacks and does so by using the six-character sequence. System.Text.Json
escapa todos os caracteres não ASCII por padrão, portanto, você não precisa fazer nada se estiver usando o StringEscapeHandling.EscapeNonAscii
no Newtonsoft.Json
.System.Text.Json
escapes all non-ASCII characters by default, so you don't need to do anything if you're using StringEscapeHandling.EscapeNonAscii
in Newtonsoft.Json
. System.Text.Json
também escapa caracteres com distinção de HTML, por padrão.System.Text.Json
also escapes HTML-sensitive characters, by default. Para obter informações sobre como substituir o System.Text.Json
comportamento padrão, consulte Personalizar codificação de caracteres.For information about how to override the default System.Text.Json
behavior, see Customize character encoding.
ComentáriosComments
Durante a desserialização, o Newtonsoft.Json
ignora comentários no JSON por padrão.During deserialization, Newtonsoft.Json
ignores comments in the JSON by default. O System.Text.Json padrão é gerar exceções para comentários porque a especificação RFC 8259 não os inclui.The System.Text.Json default is to throw exceptions for comments because the RFC 8259 specification doesn't include them. Para obter informações sobre como permitir comentários, consulte permitir comentários e vírgulas à direita.For information about how to allow comments, see Allow comments and trailing commas.
Vírgula à direitaTrailing commas
Durante a desserialização, o Newtonsoft.Json
ignora vírgulas à direita por padrão.During deserialization, Newtonsoft.Json
ignores trailing commas by default. Ele também ignora várias vírgulas à direita (por exemplo, [{"Color":"Red"},{"Color":"Green"},,]
).It also ignores multiple trailing commas (for example, [{"Color":"Red"},{"Color":"Green"},,]
). O System.Text.Json padrão é lançar exceções para vírgulas à direita porque a especificação RFC 8259 não as permite.The System.Text.Json default is to throw exceptions for trailing commas because the RFC 8259 specification doesn't allow them. Para obter informações sobre como fazer com que System.Text.Json
sejam aceitas, consulte permitir comentários e vírgulas à direita.For information about how to make System.Text.Json
accept them, see Allow comments and trailing commas. Não há como permitir várias vírgulas à direita.There's no way to allow multiple trailing commas.
Precedência de registro do conversorConverter registration precedence
A Newtonsoft.Json
precedência de registro para conversores personalizados é a seguinte:The Newtonsoft.Json
registration precedence for custom converters is as follows:
- Atributo na propriedadeAttribute on property
- Atributo no tipoAttribute on type
- Coleção de conversoresConverters collection
Essa ordem significa que um conversor personalizado na Converters
coleção é substituído por um conversor registrado pela aplicação de um atributo no nível de tipo.This order means that a custom converter in the Converters
collection is overridden by a converter that is registered by applying an attribute at the type level. Ambos os registros são substituídos por um atributo no nível de propriedade.Both of those registrations are overridden by an attribute at the property level.
A System.Text.Json precedência de registro para conversores personalizados é diferente:The System.Text.Json registration precedence for custom converters is different:
- Atributo na propriedadeAttribute on property
- Converters ColeConverters collection
- Atributo no tipoAttribute on type
A diferença aqui é que um conversor personalizado na Converters
coleção substitui um atributo no nível de tipo.The difference here is that a custom converter in the Converters
collection overrides an attribute at the type level. A intenção por trás dessa ordem de precedência é fazer com que as alterações em tempo de execução substituam as opções de tempo de design.The intention behind this order of precedence is to make run-time changes override design-time choices. Não há como alterar a precedência.There's no way to change the precedence.
Para obter mais informações sobre o registro de conversor personalizado, consulte registrar um conversor personalizado.For more information about custom converter registration, see Register a custom converter.
Profundidade máximaMaximum depth
Newtonsoft.Json
Não tem um limite de profundidade máximo por padrão.Newtonsoft.Json
doesn't have a maximum depth limit by default. System.Text.JsonHá um limite padrão de 64 e é configurável pela configuração JsonSerializerOptions.MaxDepth .For System.Text.Json there's a default limit of 64, and it's configurable by setting JsonSerializerOptions.MaxDepth.
Se você estiver usando System.Text.Json
indiretamente usando ASP.NET Core, o limite máximo de profundidade padrão será 32.If you're using System.Text.Json
indirectly by using ASP.NET Core, the default maximum depth limit is 32. O valor padrão é o mesmo para a associação de modelo e é definido na classe jsonoptions.The default value is the same as for model binding and is set in the JsonOptions class.
Cadeias JSON (nomes de propriedade e valores de cadeia de caracteres)JSON strings (property names and string values)
Durante a desserialização, o Newtonsoft.Json
aceita nomes de propriedade entre aspas duplas, aspas simples ou sem aspas.During deserialization, Newtonsoft.Json
accepts property names surrounded by double quotes, single quotes, or without quotes. Ele aceita valores de cadeia de caracteres entre aspas duplas ou aspas simples.It accepts string values surrounded by double quotes or single quotes. Por exemplo, Newtonsoft.Json
aceita o seguinte JSON:For example, Newtonsoft.Json
accepts the following JSON:
{
"name1": "value",
'name2': "value",
name3: 'value'
}
System.Text.Json
aceita somente nomes de propriedade e valores de cadeia de caracteres entre aspas duplas porque esse formato é exigido pela especificação RFC 8259 e é o único formato considerado JSON válido.System.Text.Json
only accepts property names and string values in double quotes because that format is required by the RFC 8259 specification and is the only format considered valid JSON.
Um valor entre aspas simples resulta em uma jsonexception com a seguinte mensagem:A value enclosed in single quotes results in a JsonException with the following message:
''' is an invalid start of a value.
Valores que não são de cadeia de caracteres para propriedades de cadeia de caracteresNon-string values for string properties
Newtonsoft.Json
aceita valores que não são de cadeia de caracteres, como um número ou literais true
e false
, para desserialização para propriedades do tipo cadeia de caracteres.Newtonsoft.Json
accepts non-string values, such as a number or the literals true
and false
, for deserialization to properties of type string. Aqui está um exemplo de JSON que é Newtonsoft.Json
desserializado com êxito para a seguinte classe:Here's an example of JSON that Newtonsoft.Json
successfully deserializes to the following class:
{
"String1": 1,
"String2": true,
"String3": false
}
public class ExampleClass
{
public string String1 { get; set; }
public string String2 { get; set; }
public string String3 { get; set; }
}
System.Text.Json
Não desserializa os valores que não são de cadeia de caracteres em Propriedades de cadeia de caracteres.System.Text.Json
doesn't deserialize non-string values into string properties. Um valor de não cadeia de caracteres recebido para um campo de cadeia de caracteres resulta em uma jsonexception com a seguinte mensagem:A non-string value received for a string field results in a JsonException with the following message:
The JSON value could not be converted to System.String.
Cenários usando JsonSerializerScenarios using JsonSerializer
Alguns dos cenários a seguir não têm suporte da funcionalidade interna, mas as soluções alternativas são possíveis.Some of the following scenarios aren't supported by built-in functionality, but workarounds are possible. As soluções alternativas são conversores personalizados, que podem não fornecer paridade completa com Newtonsoft.Json
funcionalidade.The workarounds are custom converters, which may not provide complete parity with Newtonsoft.Json
functionality. Para alguns deles, o código de exemplo é fornecido como exemplos.For some of these, sample code is provided as examples. Se você depender desses Newtonsoft.Json
recursos, a migração exigirá modificações em seus modelos de objeto .net ou em outras alterações de código.If you rely on these Newtonsoft.Json
features, migration will require modifications to your .NET object models or other code changes.
Para alguns dos cenários a seguir, as soluções alternativas não são práticas ou possíveis.For some of the following scenarios, workarounds are not practical or possible. Se você depender desses Newtonsoft.Json
recursos, a migração não será possível sem alterações significativas.If you rely on these Newtonsoft.Json
features, migration will not be possible without significant changes.
Permitir ou gravar números entre aspasAllow or write numbers in quotes
Newtonsoft.Json
pode serializar ou desserializar números representados por cadeias de caracteres JSON (entre aspas).Newtonsoft.Json
can serialize or deserialize numbers represented by JSON strings (surrounded by quotes). Por exemplo, ele pode aceitar: {"DegreesCelsius":"23"}
em vez de {"DegreesCelsius":23}
.For example, it can accept: {"DegreesCelsius":"23"}
instead of {"DegreesCelsius":23}
. Para habilitar esse comportamento no System.Text.Json , defina JsonSerializerOptions.NumberHandling como WriteAsString ou ou AllowReadingFromString use o atributo [JsonNumberHandling] .To enable that behavior in System.Text.Json, set JsonSerializerOptions.NumberHandling to WriteAsString or AllowReadingFromString, or use the [JsonNumberHandling] attribute.
Se você estiver usando System.Text.Json
indiretamente usando ASP.NET Core, não precisará fazer nada para obter o comportamento como Newtonsoft.Json
.If you're using System.Text.Json
indirectly by using ASP.NET Core, you don't need to do anything to get behavior like Newtonsoft.Json
. ASP.NET Core especifica os padrões da Web quando ele usa System.Text.Json
, e os padrões da Web permitem números entre aspas.ASP.NET Core specifies web defaults when it uses System.Text.Json
, and web defaults allow quoted numbers.
Para obter mais informações, consulte permitir ou gravar números entre aspas.For more information, see Allow or write numbers in quotes.
Newtonsoft.Json
pode serializar ou desserializar números representados por cadeias de caracteres JSON (entre aspas).Newtonsoft.Json
can serialize or deserialize numbers represented by JSON strings (surrounded by quotes). Por exemplo, ele pode aceitar: {"DegreesCelsius":"23"}
em vez de {"DegreesCelsius":23}
.For example, it can accept: {"DegreesCelsius":"23"}
instead of {"DegreesCelsius":23}
. Para habilitar esse comportamento no System.Text.Json no .NET Core 3,1, implemente um conversor personalizado como o exemplo a seguir.To enable that behavior in System.Text.Json in .NET Core 3.1, implement a custom converter like the following example. O conversor manipula as propriedades definidas como long
:The converter handles properties defined as long
:
- Ele os serializa como cadeias de caracteres JSON.It serializes them as JSON strings.
- Ele aceita números JSON e números entre aspas durante a desserialização.It accepts JSON numbers and numbers within quotes while deserializing.
using System;
using System.Buffers;
using System.Buffers.Text;
using System.Text.Json;
using System.Text.Json.Serialization;
namespace SystemTextJsonSamples
{
public class LongToStringConverter : JsonConverter<long>
{
public override long Read(
ref Utf8JsonReader reader, Type type, JsonSerializerOptions options)
{
if (reader.TokenType == JsonTokenType.String)
{
ReadOnlySpan<byte> span =
reader.HasValueSequence ? reader.ValueSequence.ToArray() : reader.ValueSpan;
if (Utf8Parser.TryParse(span, out long number, out int bytesConsumed) &&
span.Length == bytesConsumed)
{
return number;
}
if (long.TryParse(reader.GetString(), out number))
{
return number;
}
}
return reader.GetInt64();
}
public override void Write(
Utf8JsonWriter writer, long longValue, JsonSerializerOptions options) =>
writer.WriteStringValue(longValue.ToString());
}
}
Registre esse conversor personalizado usando um atributo em propriedades individuais long
ou adicionando o conversor à Converters coleção.Register this custom converter by using an attribute on individual long
properties or by adding the converter to the Converters collection.
Especificar o Construtor a ser usado ao desserializarSpecify constructor to use when deserializing
O Newtonsoft.Json
[JsonConstructor]
atributo permite que você especifique qual Construtor chamar ao desserializar para um poco.The Newtonsoft.Json
[JsonConstructor]
attribute lets you specify which constructor to call when deserializing to a POCO.
System.Text.Json
também tem um atributo [JsonConstructor] .System.Text.Json
also has a [JsonConstructor] attribute. Para obter mais informações, consulte tipos e registros imutáveis.For more information, see Immutable types and Records.
System.Text.Json no .NET Core 3,1 dá suporte apenas a construtores sem parâmetros.System.Text.Json in .NET Core 3.1 supports only parameterless constructors. Como alternativa, você pode chamar qualquer Construtor necessário em um conversor personalizado.As a workaround, you can call whichever constructor you need in a custom converter. Consulte o exemplo para desserializar classes e structs imutáveis.See the example for Deserialize to immutable classes and structs.
Ignorar condicionalmente uma propriedadeConditionally ignore a property
Newtonsoft.Json
o tem várias maneiras de ignorar condicionalmente uma propriedade na serialização ou desserialização:Newtonsoft.Json
has several ways to conditionally ignore a property on serialization or deserialization:
DefaultContractResolver
permite selecionar propriedades a serem incluídas ou ignoradas, com base em critérios arbitrários.DefaultContractResolver
lets you select properties to include or ignore, based on arbitrary criteria.- As
NullValueHandling
DefaultValueHandling
configurações e emJsonSerializerSettings
permitem que você especifique que todas as propriedades de valor nulo ou valor padrão devem ser ignoradas.TheNullValueHandling
andDefaultValueHandling
settings onJsonSerializerSettings
let you specify that all null-value or default-value properties should be ignored. - As
NullValueHandling
DefaultValueHandling
configurações e no[JsonProperty]
atributo permitem especificar propriedades individuais que devem ser ignoradas quando definidas como NULL ou o valor padrão.TheNullValueHandling
andDefaultValueHandling
settings on the[JsonProperty]
attribute let you specify individual properties that should be ignored when set to null or the default value.
System.Text.Json fornece as seguintes maneiras de ignorar Propriedades ou campos ao serializar:System.Text.Json provides the following ways to ignore properties or fields while serializing:
- O atributo [JsonIgnore] em uma propriedade faz com que a propriedade seja omitida do JSON durante a serialização.The [JsonIgnore] attribute on a property causes the property to be omitted from the JSON during serialization.
- A opção global IgnoreReadOnlyProperties permite ignorar todas as propriedades somente leitura.The IgnoreReadOnlyProperties global option lets you ignore all read-only properties.
- Se você estiver incluindo campos, a JsonSerializerOptions.IgnoreReadOnlyFields opção global permitirá ignorar todos os campos somente leitura.If you're Including fields, the JsonSerializerOptions.IgnoreReadOnlyFields global option lets you ignore all read-only fields.
- A
DefaultIgnoreCondition
opção global permite ignorar todas as propriedades de tipo de valor que têm valores padrãoou ignorar todas as propriedades de tipo de referência que têm valores nulos.TheDefaultIgnoreCondition
global option lets you ignore all value type properties that have default values, or ignore all reference type properties that have null values.
System.Text.Json no .NET Core 3,1 fornece as seguintes maneiras de ignorar Propriedades ao serializar:System.Text.Json in .NET Core 3.1 provides the following ways to ignore properties while serializing:
- O atributo [JsonIgnore] em uma propriedade faz com que a propriedade seja omitida do JSON durante a serialização.The [JsonIgnore] attribute on a property causes the property to be omitted from the JSON during serialization.
- A opção global IgnoreNullValues permite ignorar todas as propriedades de valor nulo.The IgnoreNullValues global option lets you ignore all null-value properties.
- A opção global IgnoreReadOnlyProperties permite ignorar todas as propriedades somente leitura.The IgnoreReadOnlyProperties global option lets you ignore all read-only properties.
Essas opções não permitem que você:These options don't let you:
- Ignorar as propriedades selecionadas com base em critérios arbitrários avaliados em tempo de execução.Ignore selected properties based on arbitrary criteria evaluated at run time.
- Ignore todas as propriedades que têm o valor padrão para o tipo.Ignore all properties that have the default value for the type.
- Ignore as propriedades selecionadas que têm o valor padrão para o tipo.Ignore selected properties that have the default value for the type.
- Ignorar propriedades selecionadas se seu valor for nulo.Ignore selected properties if their value is null.
- Ignorar as propriedades selecionadas com base em critérios arbitrários avaliados em tempo de execução.Ignore selected properties based on arbitrary criteria evaluated at run time.
Para essa funcionalidade, você pode escrever um conversor personalizado.For that functionality, you can write a custom converter. Aqui está um exemplo de POCO e um conversor personalizado para ele que ilustra essa abordagem:Here's a sample POCO and a custom converter for it that illustrates this approach:
public class WeatherForecast
{
public DateTimeOffset Date { get; set; }
public int TemperatureCelsius { get; set; }
public string Summary { get; set; }
}
using System;
using System.Text.Json;
using System.Text.Json.Serialization;
namespace SystemTextJsonSamples
{
public class WeatherForecastRuntimeIgnoreConverter : JsonConverter<WeatherForecast>
{
public override WeatherForecast Read(
ref Utf8JsonReader reader,
Type typeToConvert,
JsonSerializerOptions options)
{
if (reader.TokenType != JsonTokenType.StartObject)
{
throw new JsonException();
}
var wf = new WeatherForecast();
while (reader.Read())
{
if (reader.TokenType == JsonTokenType.EndObject)
{
return wf;
}
if (reader.TokenType == JsonTokenType.PropertyName)
{
string propertyName = reader.GetString();
reader.Read();
switch (propertyName)
{
case "Date":
DateTimeOffset date = reader.GetDateTimeOffset();
wf.Date = date;
break;
case "TemperatureCelsius":
int temperatureCelsius = reader.GetInt32();
wf.TemperatureCelsius = temperatureCelsius;
break;
case "Summary":
string summary = reader.GetString();
wf.Summary = string.IsNullOrWhiteSpace(summary) ? "N/A" : summary;
break;
}
}
}
throw new JsonException();
}
public override void Write(Utf8JsonWriter writer, WeatherForecast wf, JsonSerializerOptions options)
{
writer.WriteStartObject();
writer.WriteString("Date", wf.Date);
writer.WriteNumber("TemperatureCelsius", wf.TemperatureCelsius);
if (!string.IsNullOrWhiteSpace(wf.Summary) && wf.Summary != "N/A")
{
writer.WriteString("Summary", wf.Summary);
}
writer.WriteEndObject();
}
}
}
O conversor faz com que a Summary
propriedade seja omitida da serialização se seu valor for NULL, uma cadeia de caracteres vazia ou "N/A".The converter causes the Summary
property to be omitted from serialization if its value is null, an empty string, or "N/A".
Registre esse conversor personalizado usando um atributo na classe ou adicionando o conversor à Converters coleção.Register this custom converter by using an attribute on the class or by adding the converter to the Converters collection.
Essa abordagem requer lógica adicional se:This approach requires additional logic if:
- O POCO inclui propriedades complexas.The POCO includes complex properties.
- Você precisa manipular atributos como, por
[JsonIgnore]
exemplo, ou opções como codificadores personalizados.You need to handle attributes such as[JsonIgnore]
or options such as custom encoders.
Campos públicos e não públicosPublic and non-public fields
Newtonsoft.Json
pode serializar e desserializar campos, bem como propriedades.Newtonsoft.Json
can serialize and deserialize fields as well as properties.
No System.Text.Json , use a JsonSerializerOptions.IncludeFields configuração global ou o atributo [JsonInclude] para incluir campos públicos ao serializar ou desserializar.In System.Text.Json, use the JsonSerializerOptions.IncludeFields global setting or the [JsonInclude] attribute to include public fields when serializing or deserializing. Para obter um exemplo, consulte incluir campos.For an example, see Include fields.
System.Text.Json no .NET Core 3,1 funciona apenas com propriedades públicas.System.Text.Json in .NET Core 3.1 only works with public properties. Conversores personalizados podem fornecer essa funcionalidade.Custom converters can provide this functionality.
Preservar referências de objeto e manipular loopsPreserve object references and handle loops
Por padrão, o Newtonsoft.Json
serializa por valor.By default, Newtonsoft.Json
serializes by value. Por exemplo, se um objeto contiver duas propriedades que contêm uma referência ao mesmo Person
objeto, os valores das Person
Propriedades desse objeto serão duplicados no JSON.For example, if an object contains two properties that contain a reference to the same Person
object, the values of that Person
object's properties are duplicated in the JSON.
Newtonsoft.Json
tem uma PreserveReferencesHandling
configuração no JsonSerializerSettings
que permite serializar por referência:Newtonsoft.Json
has a PreserveReferencesHandling
setting on JsonSerializerSettings
that lets you serialize by reference:
- Um identificador de metadados é adicionado ao JSON criado para o primeiro
Person
objeto.An identifier metadata is added to the JSON created for the firstPerson
object. - O JSON que é criado para o segundo
Person
objeto contém uma referência a esse identificador em vez de valores de propriedade.The JSON that is created for the secondPerson
object contains a reference to that identifier instead of property values.
Newtonsoft.Json
também tem uma ReferenceLoopHandling
configuração que permite ignorar referências circulares em vez de gerar uma exceção.Newtonsoft.Json
also has a ReferenceLoopHandling
setting that lets you ignore circular references rather than throw an exception.
Para preservar referências e manipular referências circulares no System.Text.Json , defina JsonSerializerOptions.ReferenceHandler como Preserve .To preserve references and handle circular references in System.Text.Json, set JsonSerializerOptions.ReferenceHandler to Preserve. A ReferenceHandler.Preserve
configuração é equivalente a PreserveReferencesHandling
= PreserveReferencesHandling.All
em Newtonsoft.Json
.The ReferenceHandler.Preserve
setting is equivalent to PreserveReferencesHandling
= PreserveReferencesHandling.All
in Newtonsoft.Json
.
Como o Newtonsoft.Json ReferenceResolver, a System.Text.Json.Serialization.ReferenceResolver classe define o comportamento de preservar referências na serialização e desserialização.Like the Newtonsoft.Json ReferenceResolver, the System.Text.Json.Serialization.ReferenceResolver class defines the behavior of preserving references on serialization and deserialization. Crie uma classe derivada para especificar o comportamento personalizado.Create a derived class to specify custom behavior. Para obter um exemplo, consulte GuidReferenceResolver.For an example, see GuidReferenceResolver.
Newtonsoft.Json
Não há suporte para alguns recursos relacionados:Some related Newtonsoft.Json
features are not supported:
- JsonPropertyAttribute. IsReferenceJsonPropertyAttribute.IsReference
- JsonPropertyAttribute. ReferenceLoopHandlingJsonPropertyAttribute.ReferenceLoopHandling
- JsonSerializerSettings. ReferenceLoopHandlingJsonSerializerSettings.ReferenceLoopHandling
Para obter mais informações, consulte preservar referências e manipular referências circulares.For more information, see Preserve references and handle circular references.
System.Text.Json no .NET Core 3,1 dá suporte apenas a serialização por valor e gera uma exceção para referências circulares.System.Text.Json in .NET Core 3.1 only supports serialization by value and throws an exception for circular references.
Dicionário com chave não cadeia de caracteresDictionary with non-string key
Newtonsoft.Json
E as System.Text.Json
coleções de suporte do tipo Dictionary<TKey, TValue>
.Both Newtonsoft.Json
and System.Text.Json
support collections of type Dictionary<TKey, TValue>
. No entanto, no System.Text.Json
, TKey
deve ser um tipo primitivo, não um tipo personalizado.However, in System.Text.Json
, TKey
must be a primitive type, not a custom type. Para obter mais informações, consulte tipos de chave com suporte.For more information, see Supported key types.
Cuidado
A desserialização para um Dictionary<TKey, TValue>
onde TKey
é digitada como algo diferente de string
pode introduzir uma vulnerabilidade de segurança no aplicativo de consumo.Deserializing to a Dictionary<TKey, TValue>
where TKey
is typed as anything other than string
could introduce a security vulnerability in the consuming application. Para obter mais informações, consulte dotnet/tempo de execução # 4761.For more information, see dotnet/runtime#4761.
Newtonsoft.Json
dá suporte a coleções do tipo Dictionary<TKey, TValue>
.Newtonsoft.Json
supports collections of type Dictionary<TKey, TValue>
. O suporte interno para coleções de dicionário no System.Text.Json .NET Core 3,1 é limitado a Dictionary<string, TValue>
.The built-in support for dictionary collections in System.Text.Json in .NET Core 3.1 is limited to Dictionary<string, TValue>
. Ou seja, a chave deve ser uma cadeia de caracteres.That is, the key must be a string.
Para dar suporte a um dicionário com um inteiro ou algum outro tipo como a chave no .NET Core 3,1, crie um conversor como o exemplo em como escrever conversores personalizados.To support a dictionary with an integer or some other type as the key in .NET Core 3.1, create a converter like the example in How to write custom converters.
Tipos sem suporte internoTypes without built-in support
System.Text.Json o não fornece suporte interno para os seguintes tipos:System.Text.Json doesn't provide built-in support for the following types:
- Tipos F #, como uniões discriminadas.F# types, such as discriminated unions. Tipos de registro e tipos de registros anônimos são tratados como imutáveis POCOs e, portanto, têm suporte.Record types and anonymous record types are treated as immutable POCOs and thus are supported.
- Tipos F #, como uniões discriminadas, tipos de registroe tipos de registros anônimos.F# types, such as discriminated unions, record types, and anonymous record types.
- ExpandoObject
- TimeZoneInfo
- BigInteger
- TimeSpan
- DBNull
- Type
- ValueTuple e seus tipos genéricos associadosValueTuple and its associated generic types
Conversores personalizados podem ser implementados para tipos que não têm suporte interno.Custom converters can be implemented for types that don't have built-in support.
Serialização polimórficaPolymorphic serialization
Newtonsoft.Json
automaticamente a serialização polimórfica.Newtonsoft.Json
automatically does polymorphic serialization. Para obter informações sobre os recursos limitados de serialização polimórfico do System.Text.Json , consulte serializar Propriedades de classes derivadas.For information about the limited polymorphic serialization capabilities of System.Text.Json, see Serialize properties of derived classes.
A solução alternativa descrita aqui é definir as propriedades que podem conter classes derivadas como tipo object
.The workaround described there is to define properties that may contain derived classes as type object
. Se isso não for possível, outra opção é criar um conversor com um Write
método para a hierarquia de tipo de herança inteira, como o exemplo em como escrever conversores personalizados.If that isn't possible, another option is to create a converter with a Write
method for the whole inheritance type hierarchy like the example in How to write custom converters.
Desserialização polimórficaPolymorphic deserialization
Newtonsoft.Json
tem uma TypeNameHandling
configuração que adiciona metadados de nome de tipo ao JSON durante a serialização.Newtonsoft.Json
has a TypeNameHandling
setting that adds type name metadata to the JSON while serializing. Ele usa os metadados durante a desserialização para fazer a desserialização polimórfica.It uses the metadata while deserializing to do polymorphic deserialization. System.Text.Json pode fazer um intervalo limitado de serialização polimórfica , mas não desserialização polimórfica.System.Text.Json can do a limited range of polymorphic serialization but not polymorphic deserialization.
Para dar suporte à desserialização polimórfica, crie um conversor como o exemplo em como escrever conversores personalizados.To support polymorphic deserialization, create a converter like the example in How to write custom converters.
Desserialização de propriedades de objetoDeserialization of object properties
Quando o Newtonsoft.Json
desserializa para Object , ele:When Newtonsoft.Json
deserializes to Object, it:
- Infere o tipo de valores primitivos no conteúdo JSON (diferente de
null
) e retorna o armazenadostring
,long
,double
,boolean
ouDateTime
como um objeto em caixa.Infers the type of primitive values in the JSON payload (other thannull
) and returns the storedstring
,long
,double
,boolean
, orDateTime
as a boxed object. Os valores primitivos são valores JSON únicos, como um número JSON, Cadeia de caracteres,,true
false
ounull
.Primitive values are single JSON values such as a JSON number, string,true
,false
, ornull
. - Retorna um
JObject
ouJArray
para valores complexos na carga JSON.Returns aJObject
orJArray
for complex values in the JSON payload. Valores complexos são coleções de pares chave-valor JSON entre chaves ({}
) ou listas de valores entre colchetes ([]
).Complex values are collections of JSON key-value pairs within braces ({}
) or lists of values within brackets ([]
). As propriedades e os valores dentro das chaves ou colchetes podem ter propriedades ou valores adicionais.The properties and values within the braces or brackets can have additional properties or values. - Retorna uma referência nula quando a carga tem o
null
literal JSON.Returns a null reference when the payload has thenull
JSON literal.
System.Text.Json Armazena um Boxed JsonElement
para valores primitivos e complexos sempre que a desserialização para Object , por exemplo:System.Text.Json stores a boxed JsonElement
for both primitive and complex values whenever deserializing to Object, for example:
- Uma
object
propriedade.Anobject
property. - Um
object
valor de dicionário.Anobject
dictionary value. - Um
object
valor de matriz.Anobject
array value. - Uma raiz
object
.A rootobject
.
No entanto, System.Text.Json
null
o trata o mesmo que Newtonsoft.Json
e retorna uma referência nula quando a carga tem o null
literal JSON nela.However, System.Text.Json
treats null
the same as Newtonsoft.Json
and returns a null reference when the payload has the null
JSON literal in it.
Para implementar a inferência de tipos para object
Propriedades, crie um conversor como o exemplo em como escrever conversores personalizados.To implement type inference for object
properties, create a converter like the example in How to write custom converters.
Desserializar NULL para tipo não anulávelDeserialize null to non-nullable type
Newtonsoft.Json
o não gera uma exceção no cenário a seguir:Newtonsoft.Json
doesn't throw an exception in the following scenario:
NullValueHandling
é definido comoIgnore
eNullValueHandling
is set toIgnore
, and- Durante a desserialização, o JSON contém um valor nulo para um tipo de valor não anulável.During deserialization, the JSON contains a null value for a non-nullable value type.
No mesmo cenário, o System.Text.Json gera uma exceção.In the same scenario, System.Text.Json does throw an exception. (A configuração de manipulação nula correspondente no System.Text.Json
é JsonSerializerOptions.IgnoreNullValues = true
.)(The corresponding null-handling setting in System.Text.Json
is JsonSerializerOptions.IgnoreNullValues = true
.)
Se você possui o tipo de destino, a melhor solução alternativa é tornar a propriedade em questão anulável (por exemplo, alterar int
para int?
).If you own the target type, the best workaround is to make the property in question nullable (for example, change int
to int?
).
Outra solução alternativa é criar um conversor para o tipo, como o exemplo a seguir, que manipula valores nulos para DateTimeOffset
tipos:Another workaround is to make a converter for the type, such as the following example that handles null values for DateTimeOffset
types:
using System;
using System.Text.Json;
using System.Text.Json.Serialization;
namespace SystemTextJsonSamples
{
public class DateTimeOffsetNullHandlingConverter : JsonConverter<DateTimeOffset>
{
public override DateTimeOffset Read(
ref Utf8JsonReader reader,
Type typeToConvert,
JsonSerializerOptions options) =>
reader.TokenType == JsonTokenType.Null
? default
: reader.GetDateTimeOffset();
public override void Write(
Utf8JsonWriter writer,
DateTimeOffset dateTimeValue,
JsonSerializerOptions options) =>
writer.WriteStringValue(dateTimeValue);
}
}
Registre esse conversor personalizado usando um atributo na propriedade ou adicionando o conversor à Converters coleção.Register this custom converter by using an attribute on the property or by adding the converter to the Converters collection.
Observação: O conversor anterior manipula valores nulos de forma diferente Newtonsoft.Json
do que o faz para POCOs que especificam valores padrão.Note: The preceding converter handles null values differently than Newtonsoft.Json
does for POCOs that specify default values. Por exemplo, suponha que o código a seguir represente o objeto de destino:For example, suppose the following code represents your target object:
public class WeatherForecastWithDefault
{
public WeatherForecastWithDefault()
{
Date = DateTimeOffset.Parse("2001-01-01");
Summary = "No summary";
}
public DateTimeOffset Date { get; set; }
public int TemperatureCelsius { get; set; }
public string Summary { get; set; }
}
E suponha que o JSON a seguir seja desserializado usando o conversor anterior:And suppose the following JSON is deserialized by using the preceding converter:
{
"Date": null,
"TemperatureCelsius": 25,
"Summary": null
}
Após a desserialização, a Date
propriedade tem 1/1/0001 ( default(DateTimeOffset)
), ou seja, o valor definido no construtor é substituído.After deserialization, the Date
property has 1/1/0001 (default(DateTimeOffset)
), that is, the value set in the constructor is overwritten. Considerando o mesmo POCO e JSON, a Newtonsoft.Json
desserialização deixaria 1/1/2001 na Date
propriedade.Given the same POCO and JSON, Newtonsoft.Json
deserialization would leave 1/1/2001 in the Date
property.
Desserializar para classes e structs imutáveisDeserialize to immutable classes and structs
Newtonsoft.Json
pode desserializar para classes e structs imutáveis porque pode usar construtores com parâmetros.Newtonsoft.Json
can deserialize to immutable classes and structs because it can use constructors that have parameters.
No System.Text.Json , use o atributo [JsonConstructor] para especificar o uso de um construtor com parâmetros.In System.Text.Json, use the [JsonConstructor] attribute to specify use of a parameterized constructor. Os registros em C# 9 também são imutáveis e têm suporte como destinos de desserialização.Records in C# 9 are also immutable and are supported as deserialization targets. Para obter mais informações, consulte tipos e registros imutáveis.For more information, see Immutable types and Records.
System.Text.Json no .NET Core 3,1 dá suporte apenas a construtores públicos sem parâmetros.System.Text.Json in .NET Core 3.1 supports only public parameterless constructors. Como alternativa, você pode chamar um construtor com parâmetros em um conversor personalizado.As a workaround, you can call a constructor with parameters in a custom converter.
Aqui está um struct imutável com vários parâmetros de construtor:Here's an immutable struct with multiple constructor parameters:
public readonly struct ImmutablePoint
{
public ImmutablePoint(int x, int y)
{
X = x;
Y = y;
}
public int X { get; }
public int Y { get; }
}
E aqui está um conversor que serializa e desserializa essa estrutura:And here's a converter that serializes and deserializes this struct:
using System;
using System.Diagnostics;
using System.Text.Json;
using System.Text.Json.Serialization;
namespace SystemTextJsonSamples
{
public class ImmutablePointConverter : JsonConverter<ImmutablePoint>
{
private readonly JsonEncodedText _xName = JsonEncodedText.Encode("X");
private readonly JsonEncodedText _yName = JsonEncodedText.Encode("Y");
private readonly JsonConverter<int> _intConverter;
public ImmutablePointConverter(JsonSerializerOptions options) =>
_intConverter = options?.GetConverter(typeof(int)) is JsonConverter<int> intConverter
? intConverter
: throw new InvalidOperationException();
public override ImmutablePoint Read(
ref Utf8JsonReader reader,
Type typeToConvert,
JsonSerializerOptions options)
{
if (reader.TokenType != JsonTokenType.StartObject)
{
throw new JsonException();
};
int? x = default;
int? y = default;
// Get the first property.
reader.Read();
if (reader.TokenType != JsonTokenType.PropertyName)
{
throw new JsonException();
}
if (reader.ValueTextEquals(_xName.EncodedUtf8Bytes))
{
x = ReadProperty(ref reader, options);
}
else if (reader.ValueTextEquals(_yName.EncodedUtf8Bytes))
{
y = ReadProperty(ref reader, options);
}
else
{
throw new JsonException();
}
// Get the second property.
reader.Read();
if (reader.TokenType != JsonTokenType.PropertyName)
{
throw new JsonException();
}
if (x.HasValue && reader.ValueTextEquals(_yName.EncodedUtf8Bytes))
{
y = ReadProperty(ref reader, options);
}
else if (y.HasValue && reader.ValueTextEquals(_xName.EncodedUtf8Bytes))
{
x = ReadProperty(ref reader, options);
}
else
{
throw new JsonException();
}
reader.Read();
if (reader.TokenType != JsonTokenType.EndObject)
{
throw new JsonException();
}
return new ImmutablePoint(x.GetValueOrDefault(), y.GetValueOrDefault());
}
private int ReadProperty(ref Utf8JsonReader reader, JsonSerializerOptions options)
{
Debug.Assert(reader.TokenType == JsonTokenType.PropertyName);
reader.Read();
return _intConverter.Read(ref reader, typeof(int), options);
}
private void WriteProperty(Utf8JsonWriter writer, JsonEncodedText name, int intValue, JsonSerializerOptions options)
{
writer.WritePropertyName(name);
_intConverter.Write(writer, intValue, options);
}
public override void Write(
Utf8JsonWriter writer,
ImmutablePoint point,
JsonSerializerOptions options)
{
writer.WriteStartObject();
WriteProperty(writer, _xName, point.X, options);
WriteProperty(writer, _yName, point.Y, options);
writer.WriteEndObject();
}
}
}
Registre esse conversor personalizado adicionando o conversor à Converters coleção.Register this custom converter by adding the converter to the Converters collection.
Para obter um exemplo de um conversor semelhante que manipula propriedades genéricas abertas, consulte o conversor interno para pares de chave-valor.For an example of a similar converter that handles open generic properties, see the built-in converter for key-value pairs.
Propriedades obrigatóriasRequired properties
No Newtonsoft.Json
, você especifica que uma propriedade é exigida pela configuração Required
no [JsonProperty]
atributo.In Newtonsoft.Json
, you specify that a property is required by setting Required
on the [JsonProperty]
attribute. Newtonsoft.Json
gera uma exceção se nenhum valor for recebido no JSON para uma propriedade marcada como necessária.Newtonsoft.Json
throws an exception if no value is received in the JSON for a property marked as required.
System.Text.Json Não lançará uma exceção se nenhum valor for recebido para uma das propriedades do tipo de destino.System.Text.Json doesn't throw an exception if no value is received for one of the properties of the target type. Por exemplo, se você tiver uma WeatherForecast
classe:For example, if you have a WeatherForecast
class:
public class WeatherForecast
{
public DateTimeOffset Date { get; set; }
public int TemperatureCelsius { get; set; }
public string Summary { get; set; }
}
O JSON a seguir é desserializado sem erro:The following JSON is deserialized without error:
{
"TemperatureCelsius": 25,
"Summary": "Hot"
}
Para fazer a desserialização falhar se nenhuma Date
propriedade estiver no JSON, implemente um conversor personalizado.To make deserialization fail if no Date
property is in the JSON, implement a custom converter. O código de conversor de exemplo a seguir gera uma exceção se a Date
propriedade não estiver definida após a desserialização ser concluída:The following sample converter code throws an exception if the Date
property isn't set after deserialization is complete:
using System;
using System.Text.Json;
using System.Text.Json.Serialization;
namespace SystemTextJsonSamples
{
public class WeatherForecastRequiredPropertyConverter : JsonConverter<WeatherForecast>
{
public override WeatherForecast Read(
ref Utf8JsonReader reader,
Type type,
JsonSerializerOptions options)
{
// Don't pass in options when recursively calling Deserialize.
WeatherForecast forecast = JsonSerializer.Deserialize<WeatherForecast>(ref reader);
// Check for required fields set by values in JSON
return forecast.Date == default
? throw new JsonException("Required property not received in the JSON")
: forecast;
}
public override void Write(
Utf8JsonWriter writer,
WeatherForecast forecast, JsonSerializerOptions options)
{
// Don't pass in options when recursively calling Serialize.
JsonSerializer.Serialize(writer, forecast);
}
}
}
Registre esse conversor personalizado adicionando o conversor à JsonSerializerOptions.Converters coleção.Register this custom converter by adding the converter to the JsonSerializerOptions.Converters collection.
Esse padrão de chamar recursivamente o conversor exige que você registre o conversor usando JsonSerializerOptions , não usando um atributo.This pattern of recursively calling the converter requires that you register the converter by using JsonSerializerOptions, not by using an attribute. Se você registrar o conversor usando um atributo, o conversor personalizado chamará recursivamente a si mesmo.If you register the converter by using an attribute, the custom converter recursively calls into itself. O resultado é um loop infinito que termina em uma exceção de estouro de pilha.The result is an infinite loop that ends in a stack overflow exception.
Quando você registra o conversor usando o objeto Options, evite um loop infinito não passando o objeto Options ao chamar Serialize ou Deserialize .When you register the converter by using the options object, avoid an infinite loop by not passing in the options object when recursively calling Serialize or Deserialize. O objeto Options contém a Converters coleção.The options object contains the Converters collection. Se você passá-lo para Serialize
ou Deserialize
, o conversor personalizado chamará a si mesmo, fazendo um loop infinito que resulta em uma exceção de estouro de pilha.If you pass it in to Serialize
or Deserialize
, the custom converter calls into itself, making an infinite loop that results in a stack overflow exception. Se as opções padrão não forem viáveis, crie uma nova instância das opções com as configurações necessárias.If the default options are not feasible, create a new instance of the options with the settings that you need. Essa abordagem será lenta, pois cada nova instância armazena em cache de forma independente.This approach will be slow since each new instance caches independently.
Há um padrão alternativo que pode usar JsonConverterAttribute
o registro na classe a ser convertida.There is an alternative pattern that can use JsonConverterAttribute
registration on the class to be converted. Nessa abordagem, o código do conversor chama Serialize
ou Deserialize
em uma classe que deriva da classe a ser convertida.In this approach, the converter code calls Serialize
or Deserialize
on a class that derives from the class to be converted. A classe derivada não tem uma JsonConverterAttribute
aplicada a ela.The derived class doesn't have a JsonConverterAttribute
applied to it. No exemplo a seguir dessa alternativa:In the following example of this alternative:
WeatherForecastWithRequiredPropertyConverterAttribute
é a classe a ser desserializada e estáJsonConverterAttribute
aplicada a ela.WeatherForecastWithRequiredPropertyConverterAttribute
is the class to be deserialized and has theJsonConverterAttribute
applied to it.WeatherForecastWithoutRequiredPropertyConverterAttribute
é a classe derivada que não tem o atributo de conversor.WeatherForecastWithoutRequiredPropertyConverterAttribute
is the derived class that doesn't have the converter attribute.- O código no conversor chama
Serialize
eDeserialize
emWeatherForecastWithoutRequiredPropertyConverterAttribute
para evitar um loop infinito.The code in the converter callsSerialize
andDeserialize
onWeatherForecastWithoutRequiredPropertyConverterAttribute
to avoid an infinite loop. Há um custo de desempenho para essa abordagem na serialização devido a uma instanciação de objeto extra e à cópia de valores de propriedade.There is a performance cost to this approach on serialization due to an extra object instantiation and copying of property values.
Estes são os WeatherForecast*
tipos:Here are the WeatherForecast*
types:
[JsonConverter(typeof(WeatherForecastRequiredPropertyConverterForAttributeRegistration))]
public class WeatherForecastWithRequiredPropertyConverterAttribute
{
public DateTimeOffset Date { get; set; }
public int TemperatureCelsius { get; set; }
public string Summary { get; set; }
}
public class WeatherForecastWithoutRequiredPropertyConverterAttribute :
WeatherForecastWithRequiredPropertyConverterAttribute
{
}
E aqui está o conversor:And here is the converter:
using System;
using System.Text.Json;
using System.Text.Json.Serialization;
namespace SystemTextJsonSamples
{
public class WeatherForecastRequiredPropertyConverterForAttributeRegistration :
JsonConverter<WeatherForecastWithRequiredPropertyConverterAttribute>
{
public override WeatherForecastWithRequiredPropertyConverterAttribute Read(
ref Utf8JsonReader reader,
Type type,
JsonSerializerOptions options)
{
// OK to pass in options when recursively calling Deserialize.
WeatherForecastWithRequiredPropertyConverterAttribute forecast =
JsonSerializer.Deserialize<WeatherForecastWithoutRequiredPropertyConverterAttribute>(
ref reader,
options);
// Check for required fields set by values in JSON.
return forecast.Date == default
? throw new JsonException("Required property not received in the JSON")
: forecast;
}
public override void Write(
Utf8JsonWriter writer,
WeatherForecastWithRequiredPropertyConverterAttribute forecast,
JsonSerializerOptions options)
{
var weatherForecastWithoutConverterAttributeOnClass =
new WeatherForecastWithoutRequiredPropertyConverterAttribute
{
Date = forecast.Date,
TemperatureCelsius = forecast.TemperatureCelsius,
Summary = forecast.Summary
};
// OK to pass in options when recursively calling Serialize.
JsonSerializer.Serialize(
writer,
weatherForecastWithoutConverterAttributeOnClass,
options);
}
}
}
O conversor de propriedades necessárias exigiria lógica adicional se você precisar manipular atributos como [JsonIgnore] ou opções diferentes, como codificadores personalizados.The required properties converter would require additional logic if you need to handle attributes such as [JsonIgnore] or different options, such as custom encoders. Além disso, o código de exemplo não manipula Propriedades para as quais um valor padrão é definido no construtor.Also, the example code doesn't handle properties for which a default value is set in the constructor. E essa abordagem não diferencia os seguintes cenários:And this approach doesn't differentiate between the following scenarios:
- Uma propriedade está ausente no JSON.A property is missing from the JSON.
- Uma propriedade para um tipo não anulável está presente no JSON, mas o valor é o padrão para o tipo, como zero para um
int
.A property for a non-nullable type is present in the JSON, but the value is the default for the type, such as zero for anint
. - Uma propriedade para um tipo de valor anulável está presente no JSON, mas o valor é NULL.A property for a nullable value type is present in the JSON, but the value is null.
Especificar formato de dataSpecify date format
Newtonsoft.Json
fornece várias maneiras de controlar como as propriedades DateTime
de DateTimeOffset
tipos e são serializadas e desserializadas:Newtonsoft.Json
provides several ways to control how properties of DateTime
and DateTimeOffset
types are serialized and deserialized:
- A
DateTimeZoneHandling
configuração pode ser usada para serializar todos osDateTime
valores como datas UTC.TheDateTimeZoneHandling
setting can be used to serialize allDateTime
values as UTC dates. - A
DateFormatString
configuração e osDateTime
conversores podem ser usados para personalizar o formato de cadeias de caracteres de data.TheDateFormatString
setting andDateTime
converters can be used to customize the format of date strings.
System.Text.Json dá suporte a ISO 8601-1:2019, incluindo o perfil RFC 3339.System.Text.Json supports ISO 8601-1:2019, including the RFC 3339 profile. Esse formato é amplamente adotado, não ambíguo e faz viagens de ida e volta com precisão.This format is widely adopted, unambiguous, and makes round trips precisely. Para usar qualquer outro formato, crie um conversor personalizado.To use any other format, create a custom converter. Por exemplo, o conversor a seguir serializa e desserializa o JSON que usa a época do UNIX com o formato de fuso horário (valores como /Date(1590863400000-0700)/
):For example, the following converter serializes and deserializes JSON that uses Unix epoch with time zone format (values such as /Date(1590863400000-0700)/
):
sealed class UnixEpochDateConverter : JsonConverter<DateTimeOffset>
{
static readonly DateTimeOffset s_epoch = new DateTimeOffset(1970, 1, 1, 0, 0, 0, TimeSpan.Zero);
static readonly Regex s_regex = new Regex("^/Date\\(([^+-]+)([+-])(\\d{2})(\\d{2})\\)/$", RegexOptions.CultureInvariant);
public override DateTimeOffset Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
{
string formatted = reader.GetString();
Match match = s_regex.Match(formatted);
if (
!match.Success
|| !long.TryParse(match.Groups[1].Value, System.Globalization.NumberStyles.Integer, CultureInfo.InvariantCulture, out long unixTime)
|| !int.TryParse(match.Groups[3].Value, System.Globalization.NumberStyles.Integer, CultureInfo.InvariantCulture, out int hours)
|| !int.TryParse(match.Groups[4].Value, System.Globalization.NumberStyles.Integer, CultureInfo.InvariantCulture, out int minutes))
{
throw new Exception("Unexpected value format, unable to parse DateTimeOffset.");
}
int sign = match.Groups[2].Value[0] == '+' ? 1 : -1;
TimeSpan utcOffset = new TimeSpan(hours * sign, minutes * sign, 0);
return s_epoch.AddMilliseconds(unixTime).ToOffset(utcOffset);
}
public override void Write(Utf8JsonWriter writer, DateTimeOffset value, JsonSerializerOptions options)
{
long unixTime = Convert.ToInt64((value - s_epoch).TotalMilliseconds);
TimeSpan utcOffset = value.Offset;
string formatted = FormattableString.Invariant($"/Date({unixTime}{(utcOffset >= TimeSpan.Zero ? "+" : "-")}{utcOffset:hhmm})/");
writer.WriteStringValue(formatted);
}
}
Para obter mais informações, consulte suporte a DateTime e System.Text.Json DateTimeOffset no .For more information, see DateTime and DateTimeOffset support in System.Text.Json.
Retornos de chamadaCallbacks
Newtonsoft.Json
permite executar código personalizado em vários pontos no processo de serialização ou desserialização:Newtonsoft.Json
lets you execute custom code at several points in the serialization or deserialization process:
- OnDeserializing (ao começar a desserializar um objeto)OnDeserializing (when beginning to deserialize an object)
- OnDeserialized (quando terminar de desserializar um objeto)OnDeserialized (when finished deserializing an object)
- Onserializando (ao começar a serializar um objeto)OnSerializing (when beginning to serialize an object)
- OnSerialized (ao concluir a serialização de um objeto)OnSerialized (when finished serializing an object)
No System.Text.Json , você pode simular retornos de chamada escrevendo um conversor personalizado.In System.Text.Json, you can simulate callbacks by writing a custom converter. O exemplo a seguir mostra um conversor personalizado para um POCO.The following example shows a custom converter for a POCO. O conversor inclui um código que exibe uma mensagem em cada ponto correspondente a um Newtonsoft.Json
retorno de chamada.The converter includes code that displays a message at each point that corresponds to a Newtonsoft.Json
callback.
using System;
using System.Text.Json;
using System.Text.Json.Serialization;
namespace SystemTextJsonSamples
{
public class WeatherForecastCallbacksConverter : JsonConverter<WeatherForecast>
{
public override WeatherForecast Read(
ref Utf8JsonReader reader,
Type type,
JsonSerializerOptions options)
{
// Place "before" code here (OnDeserializing),
// but note that there is no access here to the POCO instance.
Console.WriteLine("OnDeserializing");
// Don't pass in options when recursively calling Deserialize.
WeatherForecast forecast = JsonSerializer.Deserialize<WeatherForecast>(ref reader);
// Place "after" code here (OnDeserialized)
Console.WriteLine("OnDeserialized");
return forecast;
}
public override void Write(
Utf8JsonWriter writer,
WeatherForecast forecast, JsonSerializerOptions options)
{
// Place "before" code here (OnSerializing)
Console.WriteLine("OnSerializing");
// Don't pass in options when recursively calling Serialize.
JsonSerializer.Serialize(writer, forecast);
// Place "after" code here (OnSerialized)
Console.WriteLine("OnSerialized");
}
}
}
Registre esse conversor personalizado adicionando o conversor à Converters coleção.Register this custom converter by adding the converter to the Converters collection.
Se você usar um conversor personalizado que segue o exemplo anterior:If you use a custom converter that follows the preceding sample:
- O
OnDeserializing
código não tem acesso à nova instância poco.TheOnDeserializing
code doesn't have access to the new POCO instance. Para manipular a nova instância POCO no início da desserialização, coloque esse código no Construtor POCO.To manipulate the new POCO instance at the start of deserialization, put that code in the POCO constructor. - Evite um loop infinito registrando o conversor no objeto Options e não passando o objeto Options ao chamar de forma recursiva
Serialize
ouDeserialize
.Avoid an infinite loop by registering the converter in the options object and not passing in the options object when recursively callingSerialize
orDeserialize
.
Para obter mais informações sobre conversores personalizados que chamam de forma recursiva Serialize
ou Deserialize
, consulte a seção Propriedades necessárias anteriormente neste artigo.For more information about custom converters that recursively call Serialize
or Deserialize
, see the Required properties section earlier in this article.
Setters e getters de propriedade não públicaNon-public property setters and getters
Newtonsoft.Json
pode usar setters e propriedades de propriedade privada e interna por meio do JsonProperty
atributo.Newtonsoft.Json
can use private and internal property setters and getters via the JsonProperty
attribute.
System.Text.Json dá suporte a setters e predefinidores de propriedade interna e privada por meio do atributo [JsonInclude] .System.Text.Json supports private and internal property setters and getters via the [JsonInclude] attribute. Para obter o código de exemplo, consulte acessadores de propriedade não pública.For sample code, see Non-public property accessors.
System.Text.Json no .NET Core 3,1 dá suporte apenas a setters públicos.System.Text.Json in .NET Core 3.1 supports only public setters. Conversores personalizados podem fornecer essa funcionalidade.Custom converters can provide this functionality.
Popular objetos existentesPopulate existing objects
O JsonConvert.PopulateObject
método em Newtonsoft.Json
desserializa um documento JSON para uma instância existente de uma classe, em vez de criar uma nova instância.The JsonConvert.PopulateObject
method in Newtonsoft.Json
deserializes a JSON document to an existing instance of a class, instead of creating a new instance. System.Text.Json sempre cria uma nova instância do tipo de destino usando o construtor público sem parâmetros padrão.System.Text.Json always creates a new instance of the target type by using the default public parameterless constructor. Conversores personalizados podem desserializar em uma instância existente.Custom converters can deserialize to an existing instance.
Reutilização em vez de substituir PropriedadesReuse rather than replace properties
A Newtonsoft.Json
ObjectCreationHandling
configuração permite especificar que os objetos nas propriedades devem ser reutilizados em vez de substituídos durante a desserialização.The Newtonsoft.Json
ObjectCreationHandling
setting lets you specify that objects in properties should be reused rather than replaced during deserialization. System.Text.Json sempre substitui objetos em Propriedades.System.Text.Json always replaces objects in properties. Conversores personalizados podem fornecer essa funcionalidade.Custom converters can provide this functionality.
Adicionar a coleções sem settersAdd to collections without setters
Durante a desserialização, Newtonsoft.Json
o adiciona objetos a uma coleção, mesmo que a propriedade não tenha nenhum setter.During deserialization, Newtonsoft.Json
adds objects to a collection even if the property has no setter. System.Text.Json ignora as propriedades que não têm setters.System.Text.Json ignores properties that don't have setters. Conversores personalizados podem fornecer essa funcionalidade.Custom converters can provide this functionality.
Atributos System. Runtime. SerializationSystem.Runtime.Serialization attributes
System.Text.Json Não dá suporte a atributos do System.Runtime.Serialization
namespace, como DataMemberAttribute
e IgnoreDataMemberAttribute
.System.Text.Json doesn't support attributes from the System.Runtime.Serialization
namespace, such as DataMemberAttribute
and IgnoreDataMemberAttribute
.
Números octaisOctal numbers
Newtonsoft.Json
Trata os números com um zero à esquerda como números octais.Newtonsoft.Json
treats numbers with a leading zero as octal numbers. System.Text.Json Não permite zeros à esquerda porque a especificação RFC 8259 não permite.System.Text.Json doesn't allow leading zeroes because the RFC 8259 specification doesn't allow them.
MissingMemberHandlingMissingMemberHandling
Newtonsoft.Json
pode ser configurado para gerar exceções durante a desserialização se o JSON incluir propriedades que estão ausentes no tipo de destino.Newtonsoft.Json
can be configured to throw exceptions during deserialization if the JSON includes properties that are missing in the target type. System.Text.Json ignora propriedades extras no JSON, exceto quando você usa o atributo [JsonExtensionData].System.Text.Json ignores extra properties in the JSON, except when you use the [JsonExtensionData] attribute. Não há nenhuma solução alternativa para o recurso de membro ausente.There's no workaround for the missing member feature.
TraceWriterTraceWriter
Newtonsoft.Json
permite que você depure usando um TraceWriter
para exibir logs gerados pela serialização ou desserialização.Newtonsoft.Json
lets you debug by using a TraceWriter
to view logs that are generated by serialization or deserialization. System.Text.Json Não faz registro em log.System.Text.Json doesn't do logging.
JsonDocument e Jsonelement em comparação com JToken (como JObject, JArray)JsonDocument and JsonElement compared to JToken (like JObject, JArray)
System.Text.Json.JsonDocument fornece a capacidade de analisar e criar um Modelo de Objeto do Documento somente leitura (dom) de cargas JSON existentes.System.Text.Json.JsonDocument provides the ability to parse and build a read-only Document Object Model (DOM) from existing JSON payloads. O DOM fornece acesso aleatório aos dados em uma carga JSON.The DOM provides random access to data in a JSON payload. Os elementos JSON que compõem a carga podem ser acessados por meio do JsonElement tipo.The JSON elements that compose the payload can be accessed via the JsonElement type. O JsonElement
tipo fornece APIs para converter texto JSON em tipos .net comuns.The JsonElement
type provides APIs to convert JSON text to common .NET types. JsonDocument
expõe uma RootElement propriedade.JsonDocument
exposes a RootElement property.
JsonDocument é IDisposableJsonDocument is IDisposable
JsonDocument
Cria uma exibição na memória dos dados em um buffer em pool.JsonDocument
builds an in-memory view of the data into a pooled buffer. Portanto, ao JObject
contrário JArray
de ou de Newtonsoft.Json
, o JsonDocument
tipo implementa IDisposable
e precisa ser usado dentro de um bloco Using.Therefore, unlike JObject
or JArray
from Newtonsoft.Json
, the JsonDocument
type implements IDisposable
and needs to be used inside a using block.
Retorne apenas uma JsonDocument
da sua API se você quiser transferir a propriedade de tempo de vida e descartar a responsabilidade para o chamador.Only return a JsonDocument
from your API if you want to transfer lifetime ownership and dispose responsibility to the caller. Na maioria dos cenários, isso não é necessário.In most scenarios, that isn't necessary. Se o chamador precisar trabalhar com o documento JSON inteiro, retorne o Clone do RootElement , que é um JsonElement .If the caller needs to work with the entire JSON document, return the Clone of the RootElement, which is a JsonElement. Se o chamador precisar trabalhar com um elemento específico dentro do documento JSON, retorne o Clone JsonElement .If the caller needs to work with a particular element within the JSON document, return the Clone of that JsonElement. Se você retornar o RootElement
ou um subelemento diretamente sem fazer um Clone
, o chamador não poderá acessar o retornado JsonElement
depois JsonDocument
que o proprietário for descartado.If you return the RootElement
or a sub-element directly without making a Clone
, the caller won't be able to access the returned JsonElement
after the JsonDocument
that owns it is disposed.
Aqui está um exemplo que exige que você faça um Clone
:Here's an example that requires you to make a Clone
:
public JsonElement LookAndLoad(JsonElement source)
{
string json = File.ReadAllText(source.GetProperty("fileName").GetString());
using (JsonDocument doc = JsonDocument.Parse(json))
{
return doc.RootElement.Clone();
}
}
O código anterior espera um JsonElement
que contém uma fileName
propriedade.The preceding code expects a JsonElement
that contains a fileName
property. Ele abre o arquivo JSON e cria um JsonDocument
.It opens the JSON file and creates a JsonDocument
. O método pressupõe que o chamador deseja trabalhar com o documento inteiro e, portanto, retorna o Clone
do RootElement
.The method assumes that the caller wants to work with the entire document, so it returns the Clone
of the RootElement
.
Se você receber um JsonElement
e estiver retornando um subelemento, não será necessário retornar um Clone
do subelemento.If you receive a JsonElement
and are returning a sub-element, it's not necessary to return a Clone
of the sub-element. O chamador é responsável por manter a vida o JsonDocument
que o passado JsonElement
pertence.The caller is responsible for keeping alive the JsonDocument
that the passed-in JsonElement
belongs to. Por exemplo:For example:
public JsonElement ReturnFileName(JsonElement source)
{
return source.GetProperty("fileName");
}
JsonDocument é somente leituraJsonDocument is read-only
O System.Text.Json dom não pode adicionar, remover ou modificar elementos JSON.The System.Text.Json DOM can't add, remove, or modify JSON elements. Ele foi projetado dessa forma para o desempenho e para reduzir as alocações para a análise de tamanhos de carga JSON comuns (ou seja, < 1 MB).It's designed this way for performance and to reduce allocations for parsing common JSON payload sizes (that is, < 1 MB). Se seu cenário usa atualmente um DOM modificável, uma das seguintes soluções alternativas pode ser viável:If your scenario currently uses a modifiable DOM, one of the following workarounds might be feasible:
- Para criar um
JsonDocument
do zero (ou seja, sem passar um conteúdo JSON existente para oParse
método), grave o texto JSON usando oUtf8JsonWriter
e analise a saída de para criar um novoJsonDocument
.To build aJsonDocument
from scratch (that is, without passing in an existing JSON payload to theParse
method), write the JSON text by using theUtf8JsonWriter
and parse the output from that to make a newJsonDocument
. - Para modificar um existente
JsonDocument
, use-o para gravar texto JSON, fazer alterações enquanto você escreve e analisar a saída do para criar um novoJsonDocument
.To modify an existingJsonDocument
, use it to write JSON text, making changes while you write, and parse the output from that to make a newJsonDocument
. - Para mesclar documentos JSON existentes, equivalentes
JObject.Merge
àsJContainer.Merge
APIs ou doNewtonsoft.Json
, consulte este problema do GitHub.To merge existing JSON documents, equivalent to theJObject.Merge
orJContainer.Merge
APIs fromNewtonsoft.Json
, see this GitHub issue.
Jsonelement é uma struct UnionJsonElement is a union struct
JsonDocument
expõe o RootElement
como uma propriedade do tipo JsonElement , que é um tipo Union, struct que abrange qualquer elemento JSON.JsonDocument
exposes the RootElement
as a property of type JsonElement, which is a union, struct type that encompasses any JSON element. Newtonsoft.Json
usa tipos hierárquicos dedicados como JObject
, JArray
, JToken
e assim por diante.Newtonsoft.Json
uses dedicated hierarchical types like JObject
,JArray
, JToken
, and so forth. JsonElement
é o que você pode pesquisar e enumerar e pode usar JsonElement
para materializar elementos JSON em tipos .net.JsonElement
is what you can search and enumerate over, and you can use JsonElement
to materialize JSON elements into .NET types.
Como pesquisar um JsonDocument e um Jsonelement para subelementosHow to search a JsonDocument and JsonElement for sub-elements
Procura tokens JSON usando JObject
ou JArray
de Newtonsoft.Json
tendem a ser relativamente rápidos, pois são pesquisas em algum dicionário.Searches for JSON tokens using JObject
or JArray
from Newtonsoft.Json
tend to be relatively fast because they're lookups in some dictionary. Por comparação, as pesquisas em JsonElement
exigem uma pesquisa sequencial das propriedades e, portanto, são relativamente lentas (por exemplo, ao usar TryGetProperty
).By comparison, searches on JsonElement
require a sequential search of the properties and hence is relatively slow (for example when using TryGetProperty
). System.Text.Json foi projetado para minimizar o tempo de análise inicial em vez da hora de pesquisa.System.Text.Json is designed to minimize initial parse time rather than lookup time. Portanto, use as seguintes abordagens para otimizar o desempenho ao pesquisar por um JsonDocument
objeto:Therefore, use the following approaches to optimize performance when searching through a JsonDocument
object:
- Use os enumeradores internos ( EnumerateArray e EnumerateObject ) em vez de fazer sua própria indexação ou loops.Use the built-in enumerators (EnumerateArray and EnumerateObject) rather than doing your own indexing or loops.
- Não faça uma pesquisa seqüencial no todo
JsonDocument
por meio de cada propriedade usandoRootElement
.Don't do a sequential search on the wholeJsonDocument
through every property by usingRootElement
. Em vez disso, pesquise objetos JSON aninhados com base na estrutura conhecida dos dados JSON.Instead, search on nested JSON objects based on the known structure of the JSON data. Por exemplo, se você estiver procurando umaGrade
propriedade emStudent
objetos, faça um loop pelosStudent
objetos e obtenha o valor deGrade
para cada um, em vez de Pesquisar por todos osJsonElement
objetos procurando porGrade
Propriedades.For example, if you're looking for aGrade
property inStudent
objects, loop through theStudent
objects and get the value ofGrade
for each, rather than searching through allJsonElement
objects looking forGrade
properties. Fazer o último resultará em passagens desnecessárias nos mesmos dados.Doing the latter will result in unnecessary passes over the same data.
Para obter um exemplo de código, consulte usar JsonDocument para acessar dados.For a code example, see Use JsonDocument for access to data.
Utf8JsonReader em comparação com JsonTextReaderUtf8JsonReader compared to JsonTextReader
System.Text.Json.Utf8JsonReaderé um leitor de alto desempenho, de baixa alocação e somente de encaminhamento para texto JSON codificado em UTF-8, lido de um ReadOnlySpan <byte> ou ReadOnlySequence <byte> .System.Text.Json.Utf8JsonReader is a high-performance, low allocation, forward-only reader for UTF-8 encoded JSON text, read from a ReadOnlySpan<byte> or ReadOnlySequence<byte>. O Utf8JsonReader
é um tipo de baixo nível que pode ser usado para criar analisadores e desserializadores personalizados.The Utf8JsonReader
is a low-level type that can be used to build custom parsers and deserializers.
As seções a seguir explicam os padrões de programação recomendados para o uso do Utf8JsonReader
.The following sections explain recommended programming patterns for using Utf8JsonReader
.
Utf8JsonReader é um struct de referênciaUtf8JsonReader is a ref struct
Como o Utf8JsonReader
tipo é uma struct de referência, ele tem determinadas limitações.Because the Utf8JsonReader
type is a ref struct, it has certain limitations. Por exemplo, ele não pode ser armazenado como um campo em uma classe ou struct diferente de um struct de referência.For example, it can't be stored as a field on a class or struct other than a ref struct. Para obter alto desempenho, esse tipo deve ser um, uma ref struct
vez que ele precisa armazenar em cache a entrada ReadOnlySpan <byte> , que é um struct de referência.To achieve high performance, this type must be a ref struct
since it needs to cache the input ReadOnlySpan<byte>, which itself is a ref struct. Além disso, esse tipo é mutável, pois mantém o estado.In addition, this type is mutable since it holds state. Portanto, passe-o por ref em vez de por valor.Therefore, pass it by ref rather than by value. Passá-lo por valor resultaria em uma cópia de struct e as alterações de estado não seriam visíveis para o chamador.Passing it by value would result in a struct copy and the state changes would not be visible to the caller. Isso Newtonsoft.Json
é diferente desde que o Newtonsoft.Json
JsonTextReader
é uma classe.This differs from Newtonsoft.Json
since the Newtonsoft.Json
JsonTextReader
is a class. Para obter mais informações sobre como usar structs de referência, consulte escrever código C# seguro e eficiente.For more information about how to use ref structs, see Write safe and efficient C# code.
Ler texto UTF-8Read UTF-8 text
Para obter o melhor desempenho possível ao usar o Utf8JsonReader
, leia as cargas JSON já codificadas como texto UTF-8, e não como cadeias de caracteres UTF-16.To achieve the best possible performance while using the Utf8JsonReader
, read JSON payloads already encoded as UTF-8 text rather than as UTF-16 strings. Para obter um exemplo de código, consulte filtrar dados usando Utf8JsonReader.For a code example, see Filter data using Utf8JsonReader.
Ler com um fluxo ou PipeReaderRead with a Stream or PipeReader
O Utf8JsonReader
oferece suporte à leitura de um <byte> READONLYSPAN codificado em UTF-8 ou ReadOnlySequence <byte> (que é o resultado da leitura de um PipeReader ).The Utf8JsonReader
supports reading from a UTF-8 encoded ReadOnlySpan<byte> or ReadOnlySequence<byte> (which is the result of reading from a PipeReader).
Para leitura síncrona, você pode ler a carga JSON até o final do fluxo em uma matriz de bytes e passá-la para o leitor.For synchronous reading, you could read the JSON payload until the end of the stream into a byte array and pass that into the reader. Para ler de uma cadeia de caracteres (que é codificada como UTF-16), chame UTF8 .GetBytesFor reading from a string (which is encoded as UTF-16), call UTF8.GetBytes para primeiro transcodificar a cadeia de caracteres em uma matriz de bytes codificada em UTF-8.to first transcode the string to a UTF-8 encoded byte array. Em seguida, passe-o para o Utf8JsonReader
.Then pass that to the Utf8JsonReader
.
Como o Utf8JsonReader
considera a entrada como texto JSON, uma bom (marca de ordem de byte) UTF-8 é considerada JSON inválido.Since the Utf8JsonReader
considers the input to be JSON text, a UTF-8 byte order mark (BOM) is considered invalid JSON. O chamador precisa filtrar isso antes de passar os dados para o leitor.The caller needs to filter that out before passing the data to the reader.
Para obter exemplos de código, consulte usar Utf8JsonReader.For code examples, see Use Utf8JsonReader.
Ler com ReadOnlySequence de vários segmentosRead with multi-segment ReadOnlySequence
Se a entrada JSON for um ReadOnlySpan <byte> , cada elemento JSON poderá ser acessado da ValueSpan
propriedade no leitor à medida que você passar pelo loop de leitura.If your JSON input is a ReadOnlySpan<byte>, each JSON element can be accessed from the ValueSpan
property on the reader as you go through the read loop. No entanto, se sua entrada for um <byte> ReadOnlySequence (que é o resultado da leitura de um PipeReader ), alguns elementos JSON poderão se ampliar de vários segmentos do ReadOnlySequence<byte>
objeto.However, if your input is a ReadOnlySequence<byte> (which is the result of reading from a PipeReader), some JSON elements might straddle multiple segments of the ReadOnlySequence<byte>
object. Esses elementos não podem ser acessados ValueSpan em um bloco de memória contíguo.These elements would not be accessible from ValueSpan in a contiguous memory block. Em vez disso, sempre que você tiver um multithread ReadOnlySequence<byte>
como entrada, pesquise a HasValueSequence propriedade no leitor para descobrir como acessar o elemento JSON atual.Instead, whenever you have a multi-segment ReadOnlySequence<byte>
as input, poll the HasValueSequence property on the reader to figure out how to access the current JSON element. Aqui está um padrão recomendado:Here's a recommended pattern:
while (reader.Read())
{
switch (reader.TokenType)
{
// ...
ReadOnlySpan<byte> jsonElement = reader.HasValueSequence ?
reader.ValueSequence.ToArray() :
reader.ValueSpan;
// ...
}
}
Usar ValueTextEquals para pesquisas de nome de propriedadeUse ValueTextEquals for property name lookups
Não use para fazer comparações de ValueSpan byte por byte chamando SequenceEqual pesquisas de nome de propriedade.Don't use ValueSpan to do byte-by-byte comparisons by calling SequenceEqual for property name lookups. Chame ValueTextEquals em vez disso, porque esse método desescapa quaisquer caracteres que tenham escape no JSON.Call ValueTextEquals instead, because that method unescapes any characters that are escaped in the JSON. Aqui está um exemplo que mostra como procurar uma propriedade denominada "Name":Here's an example that shows how to search for a property that is named "name":
private static readonly byte[] s_nameUtf8 = Encoding.UTF8.GetBytes("name");
while (reader.Read())
{
switch (reader.TokenType)
{
case JsonTokenType.StartObject:
total++;
break;
case JsonTokenType.PropertyName:
if (reader.ValueTextEquals(s_nameUtf8))
{
count++;
}
break;
}
}
Ler valores nulos em tipos de valores anuláveisRead null values into nullable value types
Newtonsoft.Json
fornece APIs que retornam Nullable<T> , como ReadAsBoolean
, que lidam com a Null
TokenType
para você retornando um bool?
.Newtonsoft.Json
provides APIs that return Nullable<T>, such as ReadAsBoolean
, which handles a Null
TokenType
for you by returning a bool?
. As System.Text.Json
APIs internas retornam apenas tipos de valores não anuláveis.The built-in System.Text.Json
APIs return only non-nullable value types. Por exemplo, Utf8JsonReader.GetBoolean retorna um bool
.For example, Utf8JsonReader.GetBoolean returns a bool
. Ele lançará uma exceção se encontrar Null
no JSON.It throws an exception if it finds Null
in the JSON. Os exemplos a seguir mostram duas maneiras de lidar com nulos, um retornando um tipo de valor anulável e um retornando o valor padrão:The following examples show two ways to handle nulls, one by returning a nullable value type and one by returning the default value:
public bool? ReadAsNullableBoolean()
{
_reader.Read();
if (_reader.TokenType == JsonTokenType.Null)
{
return null;
}
if (_reader.TokenType != JsonTokenType.True && _reader.TokenType != JsonTokenType.False)
{
throw new JsonException();
}
return _reader.GetBoolean();
}
public bool ReadAsBoolean(bool defaultValue)
{
_reader.Read();
if (_reader.TokenType == JsonTokenType.Null)
{
return defaultValue;
}
if (_reader.TokenType != JsonTokenType.True && _reader.TokenType != JsonTokenType.False)
{
throw new JsonException();
}
return _reader.GetBoolean();
}
MultiplataformaMulti-targeting
Se você precisar continuar a usar Newtonsoft.Json
para determinadas estruturas de destino, você pode ter vários destinos e ter duas implementações.If you need to continue to use Newtonsoft.Json
for certain target frameworks, you can multi-target and have two implementations. No entanto, isso não é trivial e exigiria uma #ifdefs
duplicação de origem.However, this is not trivial and would require some #ifdefs
and source duplication. Uma maneira de compartilhar o máximo de código possível é criar um ref struct
wrapper em volta de Utf8JsonReader
e Newtonsoft.Json
JsonTextReader
.One way to share as much code as possible is to create a ref struct
wrapper around Utf8JsonReader
and Newtonsoft.Json
JsonTextReader
. Esse wrapper unificaria a área de superfície pública ao isolar as diferenças comportamentais.This wrapper would unify the public surface area while isolating the behavioral differences. Isso permite isolar as alterações principalmente na construção do tipo, juntamente com a passagem do novo tipo por referência.This lets you isolate the changes mainly to the construction of the type, along with passing the new type around by reference. Esse é o padrão que a biblioteca Microsoft. Extensions. DependencyModel segue:This is the pattern that the Microsoft.Extensions.DependencyModel library follows:
- UnifiedJsonReader.Jsontextreader. csUnifiedJsonReader.JsonTextReader.cs
- UnifiedJsonReader. Utf8JsonReader. csUnifiedJsonReader.Utf8JsonReader.cs
Utf8JsonWriter em comparação com JsonTextWriterUtf8JsonWriter compared to JsonTextWriter
System.Text.Json.Utf8JsonWriter é uma maneira de alto desempenho para escrever texto JSON codificado em UTF-8 de tipos comuns do .NET como String
, Int32
e DateTime
.System.Text.Json.Utf8JsonWriter is a high-performance way to write UTF-8 encoded JSON text from common .NET types like String
, Int32
, and DateTime
. O gravador é um tipo de baixo nível que pode ser usado para criar serializadores personalizados.The writer is a low-level type that can be used to build custom serializers.
As seções a seguir explicam os padrões de programação recomendados para o uso do Utf8JsonWriter
.The following sections explain recommended programming patterns for using Utf8JsonWriter
.
Gravar com texto UTF-8Write with UTF-8 text
Para obter o melhor desempenho possível ao usar o Utf8JsonWriter
, grave as cargas JSON já codificadas como texto UTF-8, e não como cadeias de caracteres UTF-16.To achieve the best possible performance while using the Utf8JsonWriter
, write JSON payloads already encoded as UTF-8 text rather than as UTF-16 strings. Use JsonEncodedText para armazenar em cache e codificar previamente nomes de propriedade de cadeia de caracteres e valores como estáticos e passá-los para o gravador, em vez de usar literais de cadeia de caracteres UTF-16.Use JsonEncodedText to cache and pre-encode known string property names and values as statics, and pass those to the writer, rather than using UTF-16 string literals. Isso é mais rápido do que armazenar em cache e usar matrizes de bytes UTF-8.This is faster than caching and using UTF-8 byte arrays.
Essa abordagem também funcionará se você precisar fazer escapes personalizados.This approach also works if you need to do custom escaping. System.Text.Json
Não permite desabilitar o escape durante a gravação de uma cadeia de caracteres.System.Text.Json
doesn't let you disable escaping while writing a string. No entanto, você pode passar seu próprio personalizado JavaScriptEncoder como uma opção para o gravador, ou criar seu próprio JsonEncodedText
que usa o JavascriptEncoder
para fazer a saída e, em seguida, escrever o JsonEncodedText
em vez da cadeia de caracteres.However, you could pass in your own custom JavaScriptEncoder as an option to the writer, or create your own JsonEncodedText
that uses your JavascriptEncoder
to do the escaping, and then write the JsonEncodedText
instead of the string. Para obter mais informações, consulte Personalizar codificação de caracteres.For more information, see Customize character encoding.
Gravar valores brutosWrite raw values
O Newtonsoft.Json
WriteRawValue
método grava JSON bruto onde um valor é esperado.The Newtonsoft.Json
WriteRawValue
method writes raw JSON where a value is expected. System.Text.Json Não tem equivalente direto, mas aqui está uma solução alternativa que garante que apenas JSON válido seja gravado:System.Text.Json has no direct equivalent, but here's a workaround that ensures only valid JSON is written:
using JsonDocument doc = JsonDocument.Parse(string);
doc.WriteTo(writer);
Personalizar a saída de caracteresCustomize character escaping
A configuração StringEscapeHandling de JsonTextWriter
oferece opções para escapar de todos os caracteres não ASCII ou caracteres HTML.The StringEscapeHandling setting of JsonTextWriter
offers options to escape all non-ASCII characters or HTML characters. Por padrão, o Utf8JsonWriter
escapa todos os caracteres não ASCII e HTML.By default, Utf8JsonWriter
escapes all non-ASCII and HTML characters. Essa saída é feita para motivos de segurança de defesa intensa.This escaping is done for defense-in-depth security reasons. Para especificar uma política de saída diferente, crie um JavaScriptEncoder e defina JsonWriterOptions.Encoder .To specify a different escaping policy, create a JavaScriptEncoder and set JsonWriterOptions.Encoder. Para obter mais informações, consulte Personalizar codificação de caracteres.For more information, see Customize character encoding.
Personalizar o formato JSONCustomize JSON format
JsonTextWriter
inclui as seguintes configurações, para as quais Utf8JsonWriter
não tem equivalente:JsonTextWriter
includes the following settings, for which Utf8JsonWriter
has no equivalent:
- Recuo – especifica o número de caracteres a serem recuados.Indentation - Specifies how many characters to indent.
Utf8JsonWriter
sempre faz recuo de 2 caracteres.Utf8JsonWriter
always does 2-character indentation. - IndentChar -especifica o caractere a ser usado para recuo.IndentChar - Specifies the character to use for indentation.
Utf8JsonWriter
sempre usa espaço em branco.Utf8JsonWriter
always uses whitespace. - QuoteChar -especifica o caractere a ser usado para envolver valores de cadeia de caracteres.QuoteChar - Specifies the character to use to surround string values.
Utf8JsonWriter
sempre usa aspas duplas.Utf8JsonWriter
always uses double quotes. - QUOTENAME – especifica se os nomes de propriedade devem ser circundados com aspas.QuoteName - Specifies whether or not to surround property names with quotes.
Utf8JsonWriter
sempre circunda-os com aspas.Utf8JsonWriter
always surrounds them with quotes.
Não há soluções alternativas que permitam personalizar o JSON produzido por Utf8JsonWriter
essas maneiras.There are no workarounds that would let you customize the JSON produced by Utf8JsonWriter
in these ways.
Gravar valores nulosWrite null values
Para gravar valores nulos usando Utf8JsonWriter
, chame:To write null values by using Utf8JsonWriter
, call:
- WriteNull para gravar um par chave-valor com NULL como o valor.WriteNull to write a key-value pair with null as the value.
- WriteNullValue para gravar NULL como um elemento de uma matriz JSON.WriteNullValue to write null as an element of a JSON array.
Para uma propriedade de cadeia de caracteres, se a cadeia de caracteres for nula e WriteString WriteStringValue for equivalente a WriteNull
e WriteNullValue
.For a string property, if the string is null, WriteString and WriteStringValue are equivalent to WriteNull
and WriteNullValue
.
Gravar valores de TimeSpan, URI ou CharWrite Timespan, Uri, or char values
JsonTextWriter
fornece WriteValue
métodos para valores de TimeSpan, URIe Char .JsonTextWriter
provides WriteValue
methods for TimeSpan, Uri, and char values. Utf8JsonWriter
Não tem métodos equivalentes.Utf8JsonWriter
doesn't have equivalent methods. Em vez disso, formate esses valores como cadeias de caracteres (chamando ToString()
, por exemplo) e chame WriteStringValue .Instead, format these values as strings (by calling ToString()
, for example) and call WriteStringValue.
MultiplataformaMulti-targeting
Se você precisar continuar a usar Newtonsoft.Json
para determinadas estruturas de destino, você pode ter vários destinos e ter duas implementações.If you need to continue to use Newtonsoft.Json
for certain target frameworks, you can multi-target and have two implementations. No entanto, isso não é trivial e exigiria uma #ifdefs
duplicação de origem.However, this is not trivial and would require some #ifdefs
and source duplication. Uma maneira de compartilhar o máximo de código possível é criar um wrapper em volta de Utf8JsonWriter
e Newtonsoft
JsonTextWriter
.One way to share as much code as possible is to create a wrapper around Utf8JsonWriter
and Newtonsoft
JsonTextWriter
. Esse wrapper unificaria a área de superfície pública ao isolar as diferenças comportamentais.This wrapper would unify the public surface area while isolating the behavioral differences. Isso permite isolar as alterações principalmente na construção do tipo.This lets you isolate the changes mainly to the construction of the type. A biblioteca Microsoft. Extensions. DependencyModel segue:Microsoft.Extensions.DependencyModel library follows:
- UnifiedJsonWriter.Jsontextwriter. csUnifiedJsonWriter.JsonTextWriter.cs
- UnifiedJsonWriter. Utf8JsonWriter. csUnifiedJsonWriter.Utf8JsonWriter.cs
TypeNameHandling. All sem suporteTypeNameHandling.All not supported
A decisão de excluir TypeNameHandling.All
a funcionalidade equivalente do System.Text.Json
era intencional.The decision to exclude TypeNameHandling.All
-equivalent functionality from System.Text.Json
was intentional. Permitir que um conteúdo JSON especifique suas próprias informações de tipo é uma fonte comum de vulnerabilidades em aplicativos Web.Allowing a JSON payload to specify its own type information is a common source of vulnerabilities in web applications. Em particular, a configuração do Newtonsoft.Json
com TypeNameHandling.All
permite que o cliente remoto incorpore um aplicativo executável inteiro na própria carga JSON, de modo que durante a desserialização, o aplicativo Web extrai e executa o código inserido.In particular, configuring Newtonsoft.Json
with TypeNameHandling.All
allows the remote client to embed an entire executable application within the JSON payload itself, so that during deserialization the web application extracts and runs the embedded code. Para obter mais informações, confira sexta-feira os ataques JSON 13 PowerPoint e sexta-feira aos detalhes dos ataques JSON 13.For more information, see Friday the 13th JSON attacks PowerPoint and Friday the 13th JSON attacks details.
Recursos adicionaisAdditional resources
- System.Text.Json sobreSystem.Text.Json overview
- Como serializar e desserializar JSONHow to serialize and deserialize JSON
- Instanciar instâncias JsonSerializerOptionsInstantiate JsonSerializerOptions instances
- Habilitar a correspondência sem diferenciação de maiúsculas e minúsculasEnable case-insensitive matching
- Personalizar nomes e valores da propriedadeCustomize property names and values
- Ignorar propriedadesIgnore properties
- Permitir JSON inválidoAllow invalid JSON
- Manipular JSON de estouroHandle overflow JSON
- Preservar referênciasPreserve references
- Tipos imutáveis e acessadores não públicosImmutable types and non-public accessors
- Serialização polimórficaPolymorphic serialization
- Personalizar codificação de caracteresCustomize character encoding
- Escrever serializadores personalizados e desserializadoresWrite custom serializers and deserializers
- Gravar conversores personalizados para serialização JSONWrite custom converters for JSON serialization
- Suporte a DateTime e DateTimeOffsetDateTime and DateTimeOffset support
- System.Text.Json Referência de APISystem.Text.Json API reference
- System.Text.Json. Referência de API de serializaçãoSystem.Text.Json.Serialization API reference