次の方法で共有


System.Text.Json でサポートされている型

この記事では、シリアル化と逆シリアル化でサポートされる型の概要について説明します。

JSON オブジェクトとしてシリアル化する型

次の型は JSON オブジェクトとしてシリアル化されます。

  • クラス*
  • 構造体
  • インターフェイス
  • レコードと構造体レコード

* JSON 配列としてシリアル化 IEnumerable<T> 実装する非ディクショナリ型。 IEnumerable<T>を実装するディクショナリ型は、JSON オブジェクトとしてシリアル化されます。

次のコード スニペットは、単純な構造体のシリアル化を示しています。

public static void Main()
{
    var coordinates = new Coords(1.0, 2.0);
    string json = JsonSerializer.Serialize(coordinates);
    Console.WriteLine(json);

    // Output:
    // {"X":1,"Y":2}
}

public readonly struct Coords
{
    public Coords(double x, double y)
    {
        X = x;
        Y = y;
    }

    public double X { get; }
    public double Y { get; }
}

JSON 配列としてシリアル化する型

.NET コレクション型は JSON 配列としてシリアル化されます。 System.Text.Json.JsonSerializer は、次の場合にシリアル化のコレクション型をサポートします。

シリアライザーは、GetEnumerator() メソッドを呼び出し、要素を書き込みます。

逆シリアル化はより複雑であり、一部のコレクション型ではサポートされていません。

次のセクションでは、名前空間別に整理し、シリアル化と逆シリアル化でサポートされる型を示します。

System.Array 名前空間

種類 連載 逆シリアル化
1 次元配列 ✔️ ✔️
多次元配列
ジャグ配列 ✔️ ✔️

System.Collections 名前空間

種類 連載 逆シリアル化
ArrayList ✔️ ✔️
BitArray ✔️
DictionaryEntry ✔️ ✔️
Hashtable ✔️ ✔️
ICollection ✔️ ✔️
IDictionary ✔️ ✔️
IEnumerable ✔️ ✔️
IList ✔️ ✔️
Queue ✔️ ✔️
SortedList ✔️ ✔️
Stack * ✔️ ✔️

* タイプの サポートラウンドトリップを参照してください。

System.Collections.Generic 名前空間

種類 連載 逆シリアル化
Dictionary<TKey,TValue> * ✔️ ✔️
HashSet<T> ✔️ ✔️
IAsyncEnumerable<T> ✔️ ✔️
ICollection<T> ✔️ ✔️
IDictionary<TKey,TValue> * ✔️ ✔️
IEnumerable<T> ✔️ ✔️
IList<T> ✔️ ✔️
IReadOnlyCollection<T> ✔️ ✔️
IReadOnlyDictionary<TKey,TValue> * ✔️ ✔️
IReadOnlyList<T> ✔️ ✔️
ISet<T> ✔️ ✔️
KeyValuePair<TKey,TValue> ✔️ ✔️
LinkedList<T> ✔️ ✔️
LinkedListNode<T> ✔️
List<T> ✔️ ✔️
Queue<T> ✔️ ✔️
SortedDictionary<TKey,TValue> * ✔️ ✔️
SortedList<TKey,TValue> * ✔️ ✔️
SortedSet<T> ✔️ ✔️
Stack<T> ✔️ ✔️

*サポートされているキーの種類のを参照してください。

IAsyncEnumerable<T>の次のセクションを参照してください。

Stack タイプのラウンドトリップをサポートするを参照してください。

IAsyncEnumerable<T>

次の例では、データの非同期ソースの表現としてストリームを使用します。 ソースは、ローカル コンピューター上のファイル、またはデータベース クエリまたは Web サービス API 呼び出しの結果である可能性があります。

ストリームのシリアル化

System.Text.Json では、次の例に示すように、IAsyncEnumerable<T> 値を JSON 配列としてシリアル化できます。

using System.Text.Json;

namespace IAsyncEnumerableSerialize;

public class Program
{
    public static async Task Main()
    {
        using Stream stream = Console.OpenStandardOutput();
        var data = new { Data = PrintNumbers(3) };
        await JsonSerializer.SerializeAsync(stream, data);
    }

    static async IAsyncEnumerable<int> PrintNumbers(int n)
    {
        for (int i = 0; i < n; i++)
        {
            await Task.Delay(1000);
            yield return i;
        }
    }
}
// output:
//  {"Data":[0,1,2]}

IAsyncEnumerable<T> 値は、JsonSerializer.SerializeAsyncなどの非同期シリアル化メソッドでのみサポートされます。

ストリームの逆シリアル化

DeserializeAsyncEnumerable メソッドは、次の例に示すように、ストリーミング逆シリアル化をサポートしています。

using System.Text;
using System.Text.Json;

namespace IAsyncEnumerableDeserialize;

public class Program
{
    public static async Task Main()
    {
        using var stream = new MemoryStream(Encoding.UTF8.GetBytes("[0,1,2,3,4]"));
        await foreach (int item in JsonSerializer.DeserializeAsyncEnumerable<int>(stream))
        {
            Console.WriteLine(item);
        }
    }
}
// output:
//0
//1
//2
//3
//4

DeserializeAsyncEnumerable メソッドでは、ルート レベルの JSON 配列からの読み取りのみがサポートされます。

DeserializeAsync メソッドは IAsyncEnumerable<T>をサポートしていますが、そのシグネチャではストリーミングが許可されません。 次の例に示すように、最終的な結果は 1 つの値として返されます。

using System.Text;
using System.Text.Json;

namespace IAsyncEnumerableDeserializeNonStreaming;

public class MyPoco
{
    public IAsyncEnumerable<int>? Data { get; set; }
}

public class Program
{
    public static async Task Main()
    {
        using var stream = new MemoryStream(Encoding.UTF8.GetBytes(@"{""Data"":[0,1,2,3,4]}"));
        MyPoco? result = await JsonSerializer.DeserializeAsync<MyPoco>(stream)!;
        await foreach (int item in result!.Data!)
        {
            Console.WriteLine(item);
        }
    }
}
// output:
//0
//1
//2
//3
//4

この例では、逆シリアライザーは、逆シリアル化されたオブジェクトを返す前に、メモリ内のすべての IAsyncEnumerable<T> コンテンツをバッファーします。 逆シリアライザーは結果を返す前に JSON ペイロード全体を読み取る必要があるため、この動作が必要です。

System.Collections.Immutable 名前空間

種類 連載 逆シリアル化
IImmutableDictionary<TKey,TValue> ✔️ ✔️
IImmutableList<T> ✔️ ✔️
IImmutableQueue<T> ✔️ ✔️
IImmutableSet<T> ✔️ ✔️
IImmutableStack<T> * ✔️ ✔️
ImmutableArray<T> ✔️ ✔️
ImmutableDictionary<TKey,TValue> ✔️ ✔️
ImmutableHashSet<T> ✔️ ✔️
ImmutableQueue<T> ✔️ ✔️
ImmutableSortedDictionary<TKey,TValue> ✔️ ✔️
ImmutableSortedSet<T> ✔️ ✔️
ImmutableStack<T> * ✔️ ✔️

* タイプの サポートラウンドトリップを参照してください。

† サポート キーの種類のを参照してください。

System.Collections.Specialized 名前空間

種類 連載 逆シリアル化
BitVector32 ✔️ ❌*
HybridDictionary ✔️ ✔️
IOrderedDictionary ✔️
ListDictionary ✔️ ✔️
NameValueCollection ✔️
StringCollection ✔️
StringDictionary ✔️

* BitVector32 を逆シリアル化すると、パブリック セッターがないため、Data プロパティはスキップされます。 例外はスローされません。

System.Collections.Concurrent 名前空間

種類 連載 逆シリアル化
BlockingCollection<T> ✔️
ConcurrentBag<T> ✔️
ConcurrentDictionary<TKey,TValue> ✔️ ✔️
ConcurrentQueue<T> ✔️ ✔️
ConcurrentStack<T> * ✔️ ✔️

* タイプの サポートラウンドトリップを参照してください。

† サポート キーの種類のを参照してください。

System.Collections.ObjectModel 名前空間

種類 連載 逆シリアル化
Collection<T> ✔️ ✔️
KeyedCollection<文字列、TValue> * ✔️
ObservableCollection<T> ✔️ ✔️
ReadOnlyCollection<T> ✔️
ReadOnlyDictionary<TKey,TValue> ✔️
ReadOnlyObservableCollection<T> ✔️

*string 以外のキーはサポートされていません。

カスタム コレクション

上記のいずれかの名前空間にないコレクション型は、カスタム コレクションと見なされます。 このような型には、ユーザー定義型と、ASP.NET Core によって定義された型が含まれます。 たとえば、Microsoft.Extensions.Primitives はこのグループに含まれます。

要素型がサポートされている限り、すべてのカスタム コレクション (IEnumerableから派生するすべてのコレクション) はシリアル化でサポートされます。

逆シリアル化のサポート

カスタム コレクションは、次の場合に逆シリアル化でサポートされます。

既知の問題

次のカスタム コレクションには既知の問題があります。

  • : dotnet/runtime#29690を参照してください。
  • : dotnet/runtime#1808を参照してください。
  • DataTable: dotnet/docs#21366を参照してください。
  • : dotnet/runtime#1559を参照してください。
  • : dotnet/runtime#1559を参照してください。

既知の問題の詳細については、で開かれている問題 を参照してください。

サポートされているキーの種類

Dictionary 型と SortedList 型のキーとして使用する場合、次の型に組み込みのサポートがあります。

  • Boolean
  • Byte
  • DateTime
  • DateTimeOffset
  • Decimal
  • Double
  • Enum
  • Guid
  • Int16
  • Int32
  • Int64
  • Object (シリアル化でのみ、ランタイム型がこの一覧でサポートされている型の 1 つである場合)。
  • SByte
  • Single
  • String
  • TimeSpan
  • UInt16
  • UInt32
  • UInt64
  • Uri
  • Version

さらに、JsonConverter<T>.WriteAsPropertyName(Utf8JsonWriter, T, JsonSerializerOptions) メソッドと JsonConverter<T>.ReadAsPropertyName(Utf8JsonReader, Type, JsonSerializerOptions) メソッドを使用すると、任意の種類の辞書キーのサポートを追加できます。

サポートされていない型

シリアル化では、次の種類はサポートされていません。

System.Data 名前空間

System.Data 名前空間には、DataSetDataTable、および関連する型用の組み込みコンバーターはありません。 セキュリティ ガイダンスで説明されているように、これらの型を信頼されていない入力から逆シリアル化 安全ではありません。 ただし、これらの型をサポートするカスタム コンバーターを記述できます。 DataTableをシリアル化および逆シリアル化するカスタム コンバーター コードのサンプルについては、RoundtripDataTable.csを参照してください。

関連項目