معرفی System.Text.Json در NET Core 3.0.
نویسنده: وحید نصیری
تاریخ: ۱۳۹۸/۰۳/۲۸ ۱۳:۵
آدرس: www.dntips.ir
| مطالب | ۳۶۹۴ |
| نویسندگان | ۲۷۶ |
| گروههای مطالب | ۱۰۲۴ |
| نقشههای راه | ۱۱۹ |
| دورهها | ۱۴ |
| اشتراکها | ۱۷۹۱۴ |
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers()
.AddNewtonsoftJson()
// ...
} public class Person
{
public string FirstName { get; set; }
public string LastName { get; set; }
public DateTime? BirthDay { get; set; }
} using System;
using System.Text.Json.Serialization;
namespace ConsoleApp
{
class Program
{
static void Main(string[] args)
{
Person person = JsonSerializer.Parse<Person>(...);
string json = JsonSerializer.ToString(person);
}
}
} namespace System.Text.Json.Serialization
{
public static class JsonSerializer
{
public static object Parse(ReadOnlySpan<byte> utf8Json, Type returnType, JsonSerializerOptions options = null);
public static object Parse(string json, Type returnType, JsonSerializerOptions options = null);
public static TValue Parse<TValue>(ReadOnlySpan<byte> utf8Json, JsonSerializerOptions options = null);
public static TValue Parse<TValue>(string json, JsonSerializerOptions options = null);
public static string ToString(object value, Type type, JsonSerializerOptions options = null);
public static string ToString<TValue>(TValue value, JsonSerializerOptions options = null);
}
} public sealed class JsonSerializerOptions
{
public bool AllowTrailingCommas { get; set; }
public int DefaultBufferSize { get; set; }
public JsonNamingPolicy DictionaryKeyPolicy { get; set; }
public bool IgnoreNullValues { get; set; }
public bool IgnoreReadOnlyProperties { get; set; }
public int MaxDepth { get; set; }
public bool PropertyNameCaseInsensitive { get; set; }
public JsonNamingPolicy PropertyNamingPolicy { get; set; }
public JsonCommentHandling ReadCommentHandling { get; set; }
public bool WriteIndented { get; set; }
} // Json.NET:
var settings = new JsonSerializerSettings
{
NullValueHandling = NullValueHandling.Ignore
};
string json = JsonConvert.SerializeObject(person, settings); // JsonSerializer:
var options = new JsonSerializerOptions
{
IgnoreNullValues = true
};
string json = JsonSerializer.ToString(person, options); services.AddControllers() .AddJsonOptions(options => options.JsonSerializerOptions.WriteIndented = true);
[JsonPropertyName("birthdate")]
public DateTime? BirthDay { get; set; } var options = new JsonSerializerOptions
{
PropertyNamingPolicy = JsonNamingPolicy.CamelCase
};
string json = JsonSerializer.ToString(person, options); namespace System.Text.Json
{
public static class JsonSerializer
{
public static object Deserialize(ReadOnlySpan<byte> utf8Json, Type returnType, JsonSerializerOptions options = null);
public static object Deserialize(string json, Type returnType, JsonSerializerOptions options = null);
public static TValue Deserialize<TValue>(ReadOnlySpan<byte> utf8Json, JsonSerializerOptions options = null);
public static TValue Deserialize<TValue>(string json, JsonSerializerOptions options = null);
public static object Deserialize(ref Utf8JsonReader reader, Type returnType, JsonSerializerOptions options = null);
public static TValue Deserialize<TValue>(ref Utf8JsonReader reader, JsonSerializerOptions options = null);
public static ValueTask<object> DeserializeAsync(Stream utf8Json, Type returnType, JsonSerializerOptions options = null, CancellationToken cancellationToken = default);
public static ValueTask<TValue> DeserializeAsync<TValue>(Stream utf8Json, JsonSerializerOptions options = null, CancellationToken cancellationToken = default);
public static string Serialize(object value, Type inputType, JsonSerializerOptions options = null);
public static string Serialize<TValue>(TValue value, JsonSerializerOptions options = null);
public static void Serialize(Utf8JsonWriter writer, object value, Type inputType, JsonSerializerOptions options = null);
public static void Serialize<TValue>(Utf8JsonWriter writer, TValue value, JsonSerializerOptions options = null);
public static Task SerializeAsync(Stream utf8Json, object value, Type inputType, JsonSerializerOptions options = null, CancellationToken cancellationToken = default);
public static Task SerializeAsync<TValue>(Stream utf8Json, TValue value, JsonSerializerOptions options = null, CancellationToken cancellationToken = default);
public static byte[] SerializeToUtf8Bytes(object value, Type inputType, JsonSerializerOptions options = null);
public static byte[] SerializeToUtf8Bytes<TValue>(TValue value, JsonSerializerOptions options = null);
}
} namespace System.Text.Json
{
public sealed class JsonSerializerOptions
{
public JsonSerializerOptions();
public bool AllowTrailingCommas { get; set; }
public IList<JsonConverter> Converters { get; }
public int DefaultBufferSize { get; set; }
public JsonNamingPolicy DictionaryKeyPolicy { get; set; }
public bool IgnoreNullValues { get; set; }
public bool IgnoreReadOnlyProperties { get; set; }
public int MaxDepth { get; set; }
public bool PropertyNameCaseInsensitive { get; set; }
public JsonNamingPolicy PropertyNamingPolicy { get; set; }
public JsonCommentHandling ReadCommentHandling { get; set; }
public bool WriteIndented { get; set; }
public JsonConverter GetConverter(Type typeToConvert);
}
} namespace System.Text.Json.Serialization
{
public abstract class JsonConverter
{
public abstract bool CanConvert(Type typeToConvert);
}
} using System.Collections.Generic;
using System.Text.Json;
namespace JsonTests
{
public class Product
{
public int Id { get; set; }
public string Name { get; set; }
public bool IsInStock { get; set; }
}
class Program
{
static void Main(string[] args)
{
var products = JsonSerializer.Deserialize<List<Product>>("[{\"Id\":1026,\"Name\":\"P1\",\"IsInStock\":\"false\"}]");
}
}
} An unhandled exception of type 'System.Text.Json.JsonException' occurred in System.Text.Json.dll Inner exceptions found, see $exception in variables window for more details. Innermost exception System.InvalidOperationException : Cannot get the value of a token type 'String' as a boolean.
public class BooleanConverter : JsonConverter<bool>
{
public override bool Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
{
var value = reader.GetString();
if (value.Equals("true", StringComparison.OrdinalIgnoreCase)
|| value.Equals("yes", StringComparison.OrdinalIgnoreCase)
|| value.Equals("1", StringComparison.Ordinal))
{
return true;
}
if (value.Equals("false", StringComparison.OrdinalIgnoreCase)
|| value.Equals("no", StringComparison.OrdinalIgnoreCase)
|| value.Equals("0", StringComparison.Ordinal))
{
return false;
}
throw new NotSupportedException($"`{value}` can't be converted to `bool`.");
}
public override void Write(Utf8JsonWriter writer, bool value, JsonSerializerOptions options)
{
switch (value)
{
case true:
writer.WriteStringValue("true");
break;
case false:
writer.WriteStringValue("false");
break;
}
}
} public abstract class JsonConverter<T> : JsonConverter
{
protected internal JsonConverter();
public override bool CanConvert(Type typeToConvert);
public abstract T Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options);
public abstract void Write(Utf8JsonWriter writer, T value, JsonSerializerOptions options);
} var options = new JsonSerializerOptions();
options.Converters.Add(new BooleanConverter());
var products = JsonSerializer.Deserialize<List<Product>>(
"[{\"Id\":1026,\"Name\":\"P1\",\"IsInStock\":\"false\"}]",
options); [JsonConverter(typeof(BooleanConverter))]
public bool IsInStock { get; set; } var options = new JsonSerializerOptions() {WriteIndented = true };
options.Converters.Add(new BooleanConverter());
var data = JsonSerializer.Serialize<List<Product>>(productList, options); public class ModelIdViewModel
{
public string Id { set; get; }
} public async Task<IActionResult> RenderRole([FromBody]ModelIdViewModel model)
data: JSON.stringify({ "id": 1 }),
contentType: "application/json; charset=utf-8",
dataType: "json", public async Task<IActionResult> RenderRole([FromBody]ModelIdViewModel model)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
} {"$.id":["The JSON value could not be converted to System.String. Path: $.id | LineNumber: 0 | BytePositionInLine: 7."]} public class ModelIdViewModel
{
public int Id { set; get; }
}
public class AppJsonOptions : IConfigureOptions<JsonOptions>
{
private readonly IHttpContextAccessor _accessor;
public AppJsonOptions(IHttpContextAccessor accessor)
{
_accessor = accessor;
}
public virtual void Configure(JsonOptions options)
{
options.JsonSerializerOptions.Converters.Add(new BooleanConverter(_accessor));
}
} public void ConfigureServices(IServiceCollection services)
{
services.AddHttpContextAccessor();
services.AddSingleton<IConfigureOptions<JsonOptions>, AppJsonOptions>(); public class BooleanConverter : JsonConverter<bool>
{
private readonly IHttpContextAccessor _accessor;
public BooleanConverter(IHttpContextAccessor accessor)
{
_accessor = accessor;
}
public override bool Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
{
var testService = _accessor.HttpContext.RequestServices.GetRequiredService<TestService>();
// ...
throw new NotSupportedException();
}
public override void Write(Utf8JsonWriter writer, bool value, JsonSerializerOptions options)
{
}
} public class IntConverter : JsonConverter<int> {
public override int Read (ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) {
var value = reader.GetString ();
if (int.TryParse (value, out _))
return int.Parse (value);
throw new NotSupportedException ($"`{value}` can't be converted to `int`.");
}
public override void Write (Utf8JsonWriter writer, int value, JsonSerializerOptions options) {
writer.WriteNumberValue (value);
}
} if (int.TryParse (value, out _)) return int.Parse (value);
if (int.TryParse (value, out var result)) return result;
using System;
using System.Buffers;
using System.Buffers.Text;
using System.Text.Json;
using System.Text.Json.Serialization;
namespace Test
{
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 value, JsonSerializerOptions options)
{
writer.WriteStringValue(value.ToString());
}
}
} {"$.language":["The JSON value could not be converted to DNTCaptcha.Core.Providers.Language. Path: $.language | LineNumber: 0 | BytePositionInLine: 99."]} if (model == null || !ModelState.IsValid)
{
return BadRequest(ModelState);
} services.AddControllers().AddJsonOptions(opt =>
{
opt.JsonSerializerOptions.Converters.Add(new JsonStringEnumConverter());
}); var resultBytes = JsonSerializer.SerializeToUtf8Bytes(data,
new JsonSerializerOptions { WriteIndented = false, IgnoreNullValues = true }); var data = JsonSerializer.Deserialize<T>(new ReadOnlySpan<byte>(resultBytes));
public class SampleModel
{
public byte? Value { get; set; }
}
var options = new JsonSerializerOptions();
options.NumberHandling = System.Text.Json.Serialization.JsonNumberHandling.AllowReadingFromString;
var body = @"{""Value"":""""}";
var model = JsonSerializer.Deserialize<SampleModel>(body, options); { "Value": null } public class StringJsonConverter : JsonConverter<byte?>
{
public override byte? Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
{
return reader.TokenType switch
{
JsonTokenType.Number => reader.GetByte(),
JsonTokenType.Null => null,
JsonTokenType.String =>
byte.TryParse(reader.GetString(), NumberStyles.Number, CultureInfo.InvariantCulture, out var parsed) ? parsed : (byte?)null,
_ => throw new ArgumentOutOfRangeException(nameof(reader), reader.TokenType, "Cannot parse unexpected JSON token type.")
};
}
public override void Write(Utf8JsonWriter writer, byte? value, JsonSerializerOptions options)
{
if (value.HasValue)
{
writer.WriteNumberValue(value.Value);
}
else
{
writer.WriteNullValue();
}
}
} public string Summary { get; private set; } options = new JsonSerializerOptions
{
Encoder = JavaScriptEncoder.UnsafeRelaxedJsonEscaping,
WriteIndented = true
};
jsonString = JsonSerializer.Serialize(weatherForecast, options); var options = new JsonSerializerOptions
{
Encoder = JavaScriptEncoder.Create(UnicodeRanges.All)
}; JsonSerializerOptions options = new()
{
ReferenceHandler = ReferenceHandler.IgnoreCycles,
WriteIndented = true
};