Not
Bu sayfaya erişim yetkilendirme gerektiriyor. Oturum açmayı veya dizinleri değiştirmeyi deneyebilirsiniz.
Bu sayfaya erişim yetkilendirme gerektiriyor. Dizinleri değiştirmeyi deneyebilirsiniz.
Kitaplık, System.Text.Json değerlerini ISO 8601-1:2019 genişletilmiş profiline göre ayrıştırır ve yazar DateTime ile DateTimeOffset değerlerini işler.
Dönüştürücüler, JsonSerializer ile seri hale getirme ve seri durumdan çıkarma konusunda özel destek sağlar. Özel destek uygulamak için Utf8JsonReader ve Utf8JsonWriter de kullanabilirsiniz.
ISO 8601-1:2019 biçimi desteği
JsonSerializer, Utf8JsonReader, Utf8JsonWriter ve JsonElement türleri, ISO 8601-1:2019 biçiminin genişletilmiş profiline göre DateTime ve DateTimeOffset metin temsillerini ayrıştırır ve yazar. Örneğin, 2019-07-26T16:59:57-05:00.
DateTime ve DateTimeOffset verileri JsonSerializer olarak seri hale getirilebilir:
using System.Text.Json;
public class Example
{
private class Product
{
public string? Name { get; set; }
public DateTime ExpiryDate { get; set; }
}
public static void Main(string[] args)
{
Product p = new Product();
p.Name = "Banana";
p.ExpiryDate = new DateTime(2019, 7, 26);
string json = JsonSerializer.Serialize(p);
Console.WriteLine(json);
}
}
// The example displays the following output:
// {"Name":"Banana","ExpiryDate":"2019-07-26T00:00:00"}
DateTime ve DateTimeOffset ayrıca JsonSerializer ile seri durumdan çıkarılabilir.
using System.Text.Json;
public class Example
{
private class Product
{
public string? Name { get; set; }
public DateTime ExpiryDate { get; set; }
}
public static void Main(string[] args)
{
string json = @"{""Name"":""Banana"",""ExpiryDate"":""2019-07-26T00:00:00""}";
Product p = JsonSerializer.Deserialize<Product>(json)!;
Console.WriteLine(p.Name);
Console.WriteLine(p.ExpiryDate);
}
}
// The example displays output similar to the following:
// Banana
// 7/26/2019 12:00:00 AM
Varsayılan seçeneklerle, giriş DateTime ve DateTimeOffset metin gösterimleri genişletilmiş ISO 8601-1:2019 profiline uygun olmalıdır. Profil JsonSerializer ile uyumlu olmayan gösterimleri seri durumdan çıkarmaya çalışırsanız, JsonSerializer bir fırlatır:
using System.Text.Json;
public class Example
{
private class Product
{
public string? Name { get; set; }
public DateTime ExpiryDate { get; set; }
}
public static void Main(string[] args)
{
string json = @"{""Name"":""Banana"",""ExpiryDate"":""26/07/2019""}";
try
{
Product _ = JsonSerializer.Deserialize<Product>(json)!;
}
catch (JsonException e)
{
Console.WriteLine(e.Message);
}
}
}
// The example displays the following output:
// The JSON value could not be converted to System.DateTime. Path: $.ExpiryDate | LineNumber: 0 | BytePositionInLine: 42.
JsonDocumentve DateTime gösterimleri dahil olmak üzere DateTimeOffset bir JSON yükünün içeriğine yapılandırılmış erişim sağlar. Aşağıdaki örnekte, bir sıcaklık koleksiyonundan Pazartesi günleri ortalama sıcaklığın nasıl hesaplanması gösterilmektedir:
using System.Text.Json;
public class Example
{
private static double ComputeAverageTemperatures(string json)
{
JsonDocumentOptions options = new JsonDocumentOptions
{
AllowTrailingCommas = true
};
using (JsonDocument document = JsonDocument.Parse(json, options))
{
int sumOfAllTemperatures = 0;
int count = 0;
foreach (JsonElement element in document.RootElement.EnumerateArray())
{
DateTimeOffset date = element.GetProperty("date").GetDateTimeOffset();
if (date.DayOfWeek == DayOfWeek.Monday)
{
int temp = element.GetProperty("temp").GetInt32();
sumOfAllTemperatures += temp;
count++;
}
}
double averageTemp = (double)sumOfAllTemperatures / count;
return averageTemp;
}
}
public static void Main(string[] args)
{
string json =
@"[" +
@"{" +
@"""date"": ""2013-01-07T00:00:00Z""," +
@"""temp"": 23," +
@"}," +
@"{" +
@"""date"": ""2013-01-08T00:00:00Z""," +
@"""temp"": 28," +
@"}," +
@"{" +
@"""date"": ""2013-01-14T00:00:00Z""," +
@"""temp"": 8," +
@"}," +
@"]";
Console.WriteLine(ComputeAverageTemperatures(json));
}
}
// The example displays the following output:
// 15.5
Uyumsuz DateTime gösterimlere sahip verilen bir yükle ortalama sıcaklığı hesaplamaya kalkarsanız, JsonDocument bir FormatException oluşturur:
using System.Text.Json;
public class Example
{
private static double ComputeAverageTemperatures(string json)
{
JsonDocumentOptions options = new JsonDocumentOptions
{
AllowTrailingCommas = true
};
using (JsonDocument document = JsonDocument.Parse(json, options))
{
int sumOfAllTemperatures = 0;
int count = 0;
foreach (JsonElement element in document.RootElement.EnumerateArray())
{
DateTimeOffset date = element.GetProperty("date").GetDateTimeOffset();
if (date.DayOfWeek == DayOfWeek.Monday)
{
int temp = element.GetProperty("temp").GetInt32();
sumOfAllTemperatures += temp;
count++;
}
}
double averageTemp = (double)sumOfAllTemperatures / count;
return averageTemp;
}
}
public static void Main(string[] args)
{
// Computing the average temperatures will fail because the DateTimeOffset
// values in the payload do not conform to the extended ISO 8601-1:2019 profile.
string json =
@"[" +
@"{" +
@"""date"": ""2013/01/07 00:00:00Z""," +
@"""temp"": 23," +
@"}," +
@"{" +
@"""date"": ""2013/01/08 00:00:00Z""," +
@"""temp"": 28," +
@"}," +
@"{" +
@"""date"": ""2013/01/14 00:00:00Z""," +
@"""temp"": 8," +
@"}," +
@"]";
Console.WriteLine(ComputeAverageTemperatures(json));
}
}
// The example displays the following output:
// Unhandled exception.System.FormatException: One of the identified items was in an invalid format.
// at System.Text.Json.JsonElement.GetDateTimeOffset()
Alt düzey Utf8JsonWriter, DateTime ve DateTimeOffset verilerini yazar:
using System.Text;
using System.Text.Json;
public class Example
{
public static void Main(string[] args)
{
JsonWriterOptions options = new JsonWriterOptions
{
Indented = true
};
using (MemoryStream stream = new MemoryStream())
{
using (Utf8JsonWriter writer = new Utf8JsonWriter(stream, options))
{
writer.WriteStartObject();
writer.WriteString("date", DateTimeOffset.UtcNow);
writer.WriteNumber("temp", 42);
writer.WriteEndObject();
}
string json = Encoding.UTF8.GetString(stream.ToArray());
Console.WriteLine(json);
}
}
}
// The example output similar to the following:
// {
// "date": "2019-07-26T00:00:00+00:00",
// "temp": 42
// }
Utf8JsonReader DateTime ve DateTimeOffset verisini ayrıştırır.
using System.Text;
using System.Text.Json;
public class Example
{
public static void Main(string[] args)
{
byte[] utf8Data = Encoding.UTF8.GetBytes(@"""2019-07-26T00:00:00""");
Utf8JsonReader json = new Utf8JsonReader(utf8Data);
while (json.Read())
{
if (json.TokenType == JsonTokenType.String)
{
Console.WriteLine(json.TryGetDateTime(out DateTime datetime));
Console.WriteLine(datetime);
Console.WriteLine(json.GetDateTime());
}
}
}
}
// The example displays output similar to the following:
// True
// 7/26/2019 12:00:00 AM
// 7/26/2019 12:00:00 AM
ile Utf8JsonReaderuyumlu olmayan biçimleri okumaya çalışırsanız, bir FormatExceptionoluşturur:
using System.Text;
using System.Text.Json;
public class Example
{
public static void Main(string[] args)
{
byte[] utf8Data = Encoding.UTF8.GetBytes(@"""2019/07/26 00:00:00""");
Utf8JsonReader json = new Utf8JsonReader(utf8Data);
while (json.Read())
{
if (json.TokenType == JsonTokenType.String)
{
Console.WriteLine(json.TryGetDateTime(out DateTime datetime));
Console.WriteLine(datetime);
DateTime _ = json.GetDateTime();
}
}
}
}
// The example displays the following output:
// False
// 1/1/0001 12:00:00 AM
// Unhandled exception. System.FormatException: The JSON value is not in a supported DateTime format.
// at System.Text.Json.Utf8JsonReader.GetDateTime()
DateOnly ve TimeOnly özelliklerini seri hale getirme
.NET 7'den itibaren System.Text.Json, DateOnly ve TimeOnly türlerini serileştirmeyi ve seriden çıkarmayı destekler. Aşağıdaki nesneyi göz önünde bulundurun:
sealed file record Appointment(
Guid Id,
string Description,
DateOnly Date,
TimeOnly StartTime,
TimeOnly EndTime);
Aşağıdaki örnek, bir Appointment nesnesini serileştirir, ortaya çıkan JSON'u görüntüler ve ardından yeni bir Appointment türü örneğine geri dönüştürür. Son olarak, orijinal ve yeni seri durumdan çıkarılmış örnekler, eşit olup olmadıklarını belirlemek için karşılaştırılır ve sonuçlar konsola yazılır.
Appointment originalAppointment = new(
Id: Guid.NewGuid(),
Description: "Take dog to veterinarian.",
Date: new DateOnly(2002, 1, 13),
StartTime: new TimeOnly(5,15),
EndTime: new TimeOnly(5, 45));
string serialized = JsonSerializer.Serialize(originalAppointment);
Console.WriteLine($"Resulting JSON: {serialized}");
Appointment deserializedAppointment =
JsonSerializer.Deserialize<Appointment>(serialized)!;
bool valuesAreTheSame = originalAppointment == deserializedAppointment;
Console.WriteLine($"""
Original record has the same values as the deserialized record: {valuesAreTheSame}
""");
Önceki kodda:
- Bir
Appointmentnesne örneği oluşturulur ve değişkeneappointmentatanır. -
appointmentörneği, JsonSerializer.Serialize kullanılarak JSON'a seri hale getirilir. - Sonuçta elde edilen JSON konsola yazılır.
- JSON,
Appointmentkullanılarak JsonSerializer.Deserialize türünün yeni bir örneğine yeniden seri durumdan çıkarılır. - Özgün ve yeni seri durumdan çıkarılmış örnekler eşitlik açısından karşılaştırılır.
- Karşılaştırmanın sonucu konsola yazılır.
DateTime ve DateTimeOffset için özelleştirilmiş destek
Kullanırken JsonSerializer
Seri hale getiricinin özel ayrıştırma veya biçimlendirme gerçekleştirmesini istiyorsanız, özel dönüştürücüler uygulayabilirsiniz. Aşağıdaki bölümlerde birkaç örnek gösterilmektedir:
- DateTime(Uzaklık). Çözümle ve DateTime(Uzaklık). ToString
- Utf8Parser ve Utf8Formatter
- Yedek çözüm olarak DateTime(Offset).Parse kullanın
- Unix dönem tarih biçimini kullanma
DateTime(Offset). Ayrıştır ve DateTime(Uzaklık). ToString
Giriş DateTime veya DateTimeOffset metin gösterimlerinin biçimlerini belirleyemiyorsanız, dönüştürücü'nün okuma mantığında DateTime(Offset).Parse yöntemini kullanabilirsiniz.
Bu yöntem, .NET'in geniş desteğini kullanarak genişletilmiş ISO 8601-1:2019 profiline uymayan ISO 8601 dışı dizeler ve ISO 8601 biçimleri dahil olmak üzere çeşitli DateTime ve DateTimeOffset metin biçimlerini ayrıştırmanıza olanak tanır.
Bu yaklaşım, seri hale getiricinin yerel uygulamasını kullanmaktan daha az performanslıdır.
Serileştirme için DateTime(Offset).ToString yöntemini, dönüştürücü yazma mantığınızda kullanabilirsiniz.
Bu yöntem, standart tarih ve saat biçimlerini
using System.Diagnostics;
using System.Text.Json;
using System.Text.Json.Serialization;
using System.Text.RegularExpressions;
namespace DateTimeConverterExamples;
public class DateTimeConverterUsingDateTimeParse : JsonConverter<DateTime>
{
public override DateTime Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
{
Debug.Assert(typeToConvert == typeof(DateTime));
return DateTime.Parse(reader.GetString() ?? string.Empty);
}
public override void Write(Utf8JsonWriter writer, DateTime value, JsonSerializerOptions options)
{
writer.WriteStringValue(value.ToString());
}
}
class Program
{
private static void ParseDateTimeWithDefaultOptions()
{
DateTime _ = JsonSerializer.Deserialize<DateTime>(@"""04-10-2008 6:30 AM""");
}
private static void FormatDateTimeWithDefaultOptions()
{
Console.WriteLine(JsonSerializer.Serialize(DateTime.Parse("04-10-2008 6:30 AM -4")));
}
private static void ProcessDateTimeWithCustomConverter()
{
JsonSerializerOptions options = new JsonSerializerOptions();
options.Converters.Add(new DateTimeConverterUsingDateTimeParse());
string testDateTimeStr = "04-10-2008 6:30 AM";
string testDateTimeJson = @"""" + testDateTimeStr + @"""";
DateTime resultDateTime = JsonSerializer.Deserialize<DateTime>(testDateTimeJson, options);
Console.WriteLine(resultDateTime);
string resultDateTimeJson = JsonSerializer.Serialize(DateTime.Parse(testDateTimeStr), options);
Console.WriteLine(Regex.Unescape(resultDateTimeJson));
}
static void Main(string[] args)
{
// Parsing non-compliant format as DateTime fails by default.
try
{
ParseDateTimeWithDefaultOptions();
}
catch (JsonException e)
{
Console.WriteLine(e.Message);
}
// Formatting with default options prints according to extended ISO 8601 profile.
FormatDateTimeWithDefaultOptions();
// Using converters gives you control over the serializers parsing and formatting.
ProcessDateTimeWithCustomConverter();
}
}
// The example displays output similar to the following:
// The JSON value could not be converted to System.DateTime. Path: $ | LineNumber: 0 | BytePositionInLine: 20.
// "2008-04-10T06:30:00-04:00"
// 4/10/2008 6:30:00 AM
// "4/10/2008 6:30:00 AM"
Not
JsonConverter<T> ve TDateTime olduğunda, typeToConvert parametresi her zaman typeof(DateTime) olacaktır.
parametresi, çok biçimli durumların işlenmesinde ve performans açısından genel değerlerin typeof(T) kullanılmasında kullanışlıdır.
Utf8Parser ve Utf8Formatter
Giriş DateTime veya metin gösterimleriniz "R", "l", "O" veya DateTimeOffset "G" standart tarih ve saat biçim dizelerinden biriyle uyumluysa veya bu biçimlerden birine göre yazmak istiyorsanız, dönüştürücü mantığınızda hızlı UTF-8 tabanlı ayrıştırma ve biçimlendirme yöntemlerini kullanabilirsiniz. Bu yaklaşım, DateTime(Offset).Parse ve DateTime(Offset).ToString kullanmaktan çok daha hızlıdır.
Aşağıdaki örnekte, değerleri "R" standart biçimine göre seri hale getiren ve seri durumdan çıkaran DateTime özel bir dönüştürücü gösterilmektedir:
using System.Buffers;
using System.Buffers.Text;
using System.Diagnostics;
using System.Text.Json;
using System.Text.Json.Serialization;
namespace DateTimeConverterExamples;
// This converter reads and writes DateTime values according to the "R" standard format specifier:
// https://learn.microsoft.com/dotnet/standard/base-types/standard-date-and-time-format-strings#the-rfc1123-r-r-format-specifier.
public class DateTimeConverterForCustomStandardFormatR : JsonConverter<DateTime>
{
public override DateTime Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
{
Debug.Assert(typeToConvert == typeof(DateTime));
if (Utf8Parser.TryParse(reader.ValueSpan, out DateTime value, out _, 'R'))
{
return value;
}
throw new FormatException();
}
public override void Write(Utf8JsonWriter writer, DateTime value, JsonSerializerOptions options)
{
// The "R" standard format will always be 29 bytes.
Span<byte> utf8Date = new byte[29];
bool result = Utf8Formatter.TryFormat(value, utf8Date, out _, new StandardFormat('R'));
Debug.Assert(result);
writer.WriteStringValue(utf8Date);
}
}
class Program
{
private static void ParseDateTimeWithDefaultOptions()
{
DateTime _ = JsonSerializer.Deserialize<DateTime>(@"""Thu, 25 Jul 2019 13:36:07 GMT""");
}
private static void ProcessDateTimeWithCustomConverter()
{
JsonSerializerOptions options = new JsonSerializerOptions();
options.Converters.Add(new DateTimeConverterForCustomStandardFormatR());
string testDateTimeStr = "Thu, 25 Jul 2019 13:36:07 GMT";
string testDateTimeJson = @"""" + testDateTimeStr + @"""";
DateTime resultDateTime = JsonSerializer.Deserialize<DateTime>(testDateTimeJson, options);
Console.WriteLine(resultDateTime);
Console.WriteLine(JsonSerializer.Serialize(DateTime.Parse(testDateTimeStr), options));
}
static void Main(string[] args)
{
// Parsing non-compliant format as DateTime fails by default.
try
{
ParseDateTimeWithDefaultOptions();
}
catch (JsonException e)
{
Console.WriteLine(e.Message);
}
// Using converters gives you control over the serializers parsing and formatting.
ProcessDateTimeWithCustomConverter();
}
}
// The example displays output similar to the following:
// The JSON value could not be converted to System.DateTime.Path: $ | LineNumber: 0 | BytePositionInLine: 31.
// 7/25/2019 1:36:07 PM
// "Thu, 25 Jul 2019 09:36:07 GMT"
Not
"R" standart biçimi her zaman 29 karakter uzunluğunda olacaktır.
"l" (küçük harf "L") biçimi, yalnızca ve Utf8Parser türleri tarafından desteklendiği için diğer Utf8Formatter ile birlikte belgelenmez. Biçim küçük harf RFC 1123'tür ("R" biçiminin küçük harfli sürümü). Örneğin, "per, 25 temmuz 2019 06:36:07 gmt".
DateTime(Offset)'i ayrıştırma işlemi için bir geri dönüş olarak kullanın.
Giriş DateTime veya DateTimeOffset verilerinizin genişletilmiş ISO 8601-1:2019 profiline uymasını bekliyorsanız, seri hale getiricinin yerel ayrıştırma mantığını kullanabilirsiniz. Geri dönüş mekanizması da uygulayabilirsiniz. Aşağıdaki örnek, DateTime kullanılarak TryGetDateTime(DateTime) metin gösteriminin ayrıştırılmasının başarısız olmasının ardından, Parse(String) kullanılarak verilerin başarıyla ayrıştırıldığını göstermektedir.
using System.Diagnostics;
using System.Text.Json;
using System.Text.Json.Serialization;
using System.Text.RegularExpressions;
namespace DateTimeConverterExamples;
public class DateTimeConverterUsingDateTimeParseAsFallback : JsonConverter<DateTime>
{
public override DateTime Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
{
Debug.Assert(typeToConvert == typeof(DateTime));
if (!reader.TryGetDateTime(out DateTime value))
{
value = DateTime.Parse(reader.GetString()!);
}
return value;
}
public override void Write(Utf8JsonWriter writer, DateTime value, JsonSerializerOptions options)
{
writer.WriteStringValue(value.ToString("dd/MM/yyyy"));
}
}
class Program
{
private static void ParseDateTimeWithDefaultOptions()
{
DateTime _ = JsonSerializer.Deserialize<DateTime>(@"""2019-07-16 16:45:27.4937872+00:00""");
}
private static void ProcessDateTimeWithCustomConverter()
{
JsonSerializerOptions options = new JsonSerializerOptions();
options.Converters.Add(new DateTimeConverterUsingDateTimeParseAsFallback());
string testDateTimeStr = "2019-07-16 16:45:27.4937872+00:00";
string testDateTimeJson = @"""" + testDateTimeStr + @"""";
DateTime resultDateTime = JsonSerializer.Deserialize<DateTime>(testDateTimeJson, options);
Console.WriteLine(resultDateTime);
string resultDateTimeJson = JsonSerializer.Serialize(DateTime.Parse(testDateTimeStr), options);
Console.WriteLine(Regex.Unescape(resultDateTimeJson));
}
static void Main(string[] args)
{
// Parsing non-compliant format as DateTime fails by default.
try
{
ParseDateTimeWithDefaultOptions();
}
catch (JsonException e)
{
Console.WriteLine(e.Message);
}
// Using converters gives you control over the serializers parsing and formatting.
ProcessDateTimeWithCustomConverter();
}
}
// The example displays output similar to the following:
// The JSON value could not be converted to System.DateTime.Path: $ | LineNumber: 0 | BytePositionInLine: 35.
// 7/16/2019 4:45:27 PM
// "16/07/2019"
Unix dönem tarih biçimini kullanma
Aşağıdaki dönüştürücüler Unix dönem biçimini zaman dilimi farkı ile ya da (örneğin /Date(1590863400000-0700)/ veya /Date(1590863400000)/ gibi değerlerle) olmadan işler.
sealed class UnixEpochDateTimeOffsetConverter : System.Text.Json.Serialization.JsonConverter<DateTimeOffset>
{
static readonly DateTimeOffset s_epoch = new(1970, 1, 1, 0, 0, 0, TimeSpan.Zero);
static readonly Regex s_regex = new(
"^/Date\\(([+-]*\\d+)([+-])(\\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, NumberStyles.Integer, CultureInfo.InvariantCulture, out long unixTime)
|| !int.TryParse(match.Groups[3].Value, NumberStyles.Integer, CultureInfo.InvariantCulture, out int hours)
|| !int.TryParse(match.Groups[4].Value, NumberStyles.Integer, CultureInfo.InvariantCulture, out int minutes))
{
throw new System.Text.Json.JsonException();
}
int sign = match.Groups[2].Value[0] == '+' ? 1 : -1;
TimeSpan utcOffset = new(hours * sign, minutes * sign, 0);
return s_epoch.AddMilliseconds(unixTime).ToOffset(utcOffset);
}
public override void Write(
Utf8JsonWriter writer,
DateTimeOffset value,
JsonSerializerOptions options)
{
long unixTime = value.ToUnixTimeMilliseconds();
TimeSpan utcOffset = value.Offset;
string formatted = string.Create(
CultureInfo.InvariantCulture,
$"/Date({unixTime}{(utcOffset >= TimeSpan.Zero ? "+" : "-")}{utcOffset:hhmm})/");
writer.WriteStringValue(formatted);
}
}
sealed class UnixEpochDateTimeConverter : System.Text.Json.Serialization.JsonConverter<DateTime>
{
static readonly DateTime s_epoch = new(1970, 1, 1, 0, 0, 0);
static readonly Regex s_regex = new(
"^/Date\\(([+-]*\\d+)\\)/$",
RegexOptions.CultureInvariant);
public override DateTime 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, NumberStyles.Integer, CultureInfo.InvariantCulture, out long unixTime))
{
throw new System.Text.Json.JsonException();
}
return s_epoch.AddMilliseconds(unixTime);
}
public override void Write(
Utf8JsonWriter writer,
DateTime value,
JsonSerializerOptions options)
{
long unixTime = (value - s_epoch).Ticks / TimeSpan.TicksPerMillisecond;
string formatted = string.Create(CultureInfo.InvariantCulture, $"/Date({unixTime})/");
writer.WriteStringValue(formatted);
}
}
Kullanırken Utf8JsonWriter
ile DateTimebir özel DateTimeOffset veya Utf8JsonWriter metin gösterimi yazmak istiyorsanız, özel gösteriminizi bir String, , ReadOnlySpan<Byte>ReadOnlySpan<Char>veya JsonEncodedTextolarak biçimlendirebilir ve ardından ilgili Utf8JsonWriter.WriteStringValue veya Utf8JsonWriter.WriteString yönteme geçirebilirsiniz.
Aşağıdaki örnekte özel bir DateTime biçiminin ToString(String, IFormatProvider) ile nasıl oluşturulabileceği ve ardından WriteStringValue(String) yöntemiyle nasıl yazılacağı gösterilmektedir:
using System.Globalization;
using System.Text;
using System.Text.Json;
public class Example
{
public static void Main(string[] args)
{
var options = new JsonWriterOptions
{
Indented = true
};
using (var stream = new MemoryStream())
{
using (var writer = new Utf8JsonWriter(stream, options))
{
string dateStr = DateTime.UtcNow.ToString("F", CultureInfo.InvariantCulture);
writer.WriteStartObject();
writer.WriteString("date", dateStr);
writer.WriteNumber("temp", 42);
writer.WriteEndObject();
}
string json = Encoding.UTF8.GetString(stream.ToArray());
Console.WriteLine(json);
}
}
}
// The example displays output similar to the following:
// {
// "date": "Tuesday, 27 August 2019 19:21:44",
// "temp": 42
// }
Kullanırken Utf8JsonReader
Eğer bir özel DateTime veya DateTimeOffset metin gösterimi ile Utf8JsonReader okumak istiyorsanız, String yöntemini kullanarak geçerli JSON belirtecinin değerini bir GetString() olarak alabilir ve ardından özel mantıkla değeri ayrıştırabilirsiniz.
Aşağıdaki örnek, özel DateTimeOffset metin gösteriminin GetString() yöntemi kullanılarak nasıl alınabileceğini ve ardından ParseExact(String, String, IFormatProvider) kullanılarak nasıl ayrıştırılabileceğini gösterir.
using System.Globalization;
using System.Text;
using System.Text.Json;
public class Example
{
public static void Main(string[] args)
{
byte[] utf8Data = Encoding.UTF8.GetBytes(@"""Friday, 26 July 2019 00:00:00""");
var json = new Utf8JsonReader(utf8Data);
while (json.Read())
{
if (json.TokenType == JsonTokenType.String)
{
string value = json.GetString();
DateTimeOffset dto = DateTimeOffset.ParseExact(value, "F", CultureInfo.InvariantCulture);
Console.WriteLine(dto);
}
}
}
}
// The example displays output similar to the following:
// 7/26/2019 12:00:00 AM -04:00
System.Text.Json'da genişletilmiş ISO 8601-1:2019 profili
Tarih ve saat bileşenleri
'de System.Text.Json uygulanan genişletilmiş ISO 8601-1:2019 profili, tarih ve saat gösterimleri için aşağıdaki bileşenleri tanımlar. Bu bileşenler, ayrıştırma, biçimlendirme DateTime ve DateTimeOffset gösterimler sırasında desteklenen çeşitli ayrıntı düzeylerini tanımlamak için kullanılır.
| Bileşen | Biçim | Açıklama |
|---|---|---|
| Yıl | "yyyy" | 0001-9999 |
| Ay | MM | 01.12 |
| Gün | "dd" | 01-28, 01-29, 01-30, 01-31 ay/yıl temelinde. |
| Saat | HH | 00-23 |
| Dakika | "mm" | 00-59 |
| İkinci | "ss" | 00-59 |
| İkinci kesir | "FFFFFFF" | En az bir basamak, en fazla 16 basamak. |
| Zaman farkı | "K" | "Z" veya "('+'/'-')HH':'mm". |
| Kısmi süre | "HH':'mm':'ss[FFFFFFF]" | UTC saat dilimi bilgisi olmayan zaman. |
| Tam tarih | "yyyy'-'MM'-'dd" | Takvim tarihi. |
| Tam zamanlı | "'Kısmi zaman' K" | Günün UTC zamanı veya yerel saat, yerel saat ile UTC arasındaki saat farkı ile birlikte. |
| Tarih ve saat | "'Tam tarih''T''Tam saat'" | Takvim tarihi ve saati, örneğin, 2019-07-26T16:59:57-05:00. |
Ayrıştırma desteği
Ayrıştırma için aşağıdaki ayrıntı düzeyleri tanımlanır:
'Tam tarih'
- "yyyy'-'MM'-'dd"
"'Tam tarih'''T''Saat'':''Dakika'"
- "yyyy'-'MM'-'dd'T'HH':'mm"
"'Tam tarih'''T''Kısmi saat'"
- "yyyy'-'MM'-'dd'T'HH':'mm':'ss" (Sıralanabilir ("s") Biçim Tanımlayıcısı)
- "yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'FFFFFFF"
"'Tam tarih'''T''Saat'':''Dakika''Zaman farkı'"
- "yyyy'-'MM'-'dd'T'HH':'mmZ"
- "yyyy'-'MM'-'dd'T'HH':'mm('+'/'-')HH':'mm"
Tarih ve saat
- yyyy'-'MM'-'dd'T'HH':'mm':'ssZ
- yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'FFFFFFFZ
- "yyyy'-'MM'-'dd'T'HH':'mm':'ss('+'/'-')HH':'mm"
- "yyyy'-'MM'-'dd'T'HH':'mm':'ss'.' FFFFFFF('+'/'-')HH':'mm"
Bu ayrıntı düzeyi, tarih ve saat bilgilerinin değişimi için kullanılan ve iso 8601'in yaygın olarak benimsenen bir profili olan RFC 3339 ile uyumludur. Ancak, uygulamada birkaç kısıtlama
System.Text.Jsonvardır.- RFC 3339, kesirli saniye basamak sayısı üst sınırını belirtmez, ancak kesirli saniye bölümü varsa en az bir rakamın dönemi izlemesi gerektiğini belirtir. içindeki
System.Text.Jsonuygulaması en fazla 16 basamağı (diğer programlama dilleri ve çerçeveleriyle birlikte çalışma desteği için) sağlar, ancak yalnızca ilk yediyi ayrıştırmaktadır. Okuma sırasında JsonException veDateTimeörneklerinde 16'dan fazla kesirli saniye basamağı varsa birDateTimeOffsetatılır. - RFC 3339, "T" ve "Z" karakterlerinin sırasıyla "t" veya "z" olmasını sağlar, ancak uygulamaların desteği yalnızca büyük harf çeşitlemeleriyle sınırlamasına olanak tanır. içindeki
System.Text.Jsonuygulaması için "T" ve "Z" olması gerekir. Bir hata, giriş yükleri JsonException veDateTimeörneği okunduğunda "t" veya "z" içeriyorsa atılır. - RFC 3339, tarih ve saat bölümlerinin "T" ile ayrıldığını belirtir, ancak uygulamaların bunları boşlukla (" ") ayırmasına izin verir.
System.Text.Jsontarih ve saat bölümlerinin "T" ile ayrılmasını gerektirir. Giriş yükleri boşluk (" ") içeriyorsa ve JsonException veDateTimeörnekleri okunurken birDateTimeOffsetatılır.
Saniyeler için ondalık kesirler varsa, en az bir basamak olmalıdır.
2019-07-26T00:00:00. izin verilmiyor.
En fazla 16 kesirli basamağı kullanabilirsiniz ancak yalnızca ilk yedi basamak ayrıştırılır. Bunun ötesindeki her şey sıfır olarak kabul edilir.
Örneğin, 2019-07-26T00:00:00.1234567890'nin 2019-07-26T00:00:00.1234567 gibi ayrıştırılacak.
Bu yaklaşım, bu çözünürlükle sınırlı olan DateTime uygulamasıyla uyumluluğu korur.
Artık saniyeler desteklenmiyor.
Biçimlendirme desteği
Biçimlendirme için aşağıdaki ayrıntı düzeyleri tanımlanır:
"'Tam tarih'''T''Kısmi saat'"
"yyyy'-'MM'-'dd'T'HH':'mm':'ss" (Sıralanabilir ("s") Biçim Tanımlayıcısı)
Kesirli saniyeler ve kaydırma bilgisi olmadan DateTime biçimlendirmek için kullanılır.
"yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'FFFFFFF"
Kesirli saniyelerle, ancak zaman dilimi bilgisi olmadan bir DateTime biçimlendirmek için kullanılır.
Tarih ve saat
yyyy'-'MM'-'dd'T'HH':'mm':'ssZ
Kesirli saniye olmadan ancak UTC farkı ile DateTime biçimlendirmek için kullanılır.
yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'FFFFFFFZ
Kesirli saniyelerle ve UTC ofseti ile DateTime'yi biçimlendirmek için kullanılır.
"yyyy'-'MM'-'dd'T'HH':'mm':'ss('+'/'-')HH':'mm"
Kesirli saniyeler olmadan, ancak yerel öteleme ile DateTime veya DateTimeOffset biçimlendirmek için kullanılır.
"yyyy'-'MM'-'dd'T'HH':'mm':'ss'.' FFFFFFF('+'/'-')HH':'mm"
Kesirli saniyeler ve yerel zaman farkı ile DateTime veya DateTimeOffset biçimlendirmek için kullanılır.
Bu ayrıntı düzeyi RFC 3339 ile uyumludur.
çift yönlü format gösterimi bir DateTime veya DateTimeOffset örneğinin kesirli saniyelerinde sondaki sıfırlara sahipse, JsonSerializer ve Utf8JsonWriter örneği sondaki sıfırlar olmadan biçimlendirecektir.
Örneğin, DateTime temsili olan bir 2019-04-24T14:50:17.1010000Z örneği, 2019-04-24T14:50:17.101Z ve JsonSerializer tarafından Utf8JsonWriter olarak biçimlendirilir.
gidiş-dönüş formatı temsilinde bir DateTime veya DateTimeOffset örneğinin kesirli saniyeleri yalnızca sıfırlardan oluşuyorsa, o zaman JsonSerializer ve Utf8JsonWriter bu örneği kesirli saniyeler olmadan biçimlendirir.
Örneğin, DateTime temsili olan bir 2019-04-24T14:50:17.0000000+02:00 örneği, 2019-04-24T14:50:17+02:00 ve JsonSerializer tarafından Utf8JsonWriter olarak biçimlendirilir.
Kesirli saniye basamaklarında sıfırların kesilmesi, bir gidiş dönüşteki bilgilerin yazılması için gereken en küçük çıkışı sağlar.
En fazla yedi kesirli saniye basamağı yazılır. Bu maksimum, bu çözünürlükle sınırlı olan DateTime uygulamasıyla hizalanır.