12

誰もこの質問についてまだ質問していない理由はわかりませんが、IContractResolverインターフェイスを使用して特定のオブジェクトの単純な型のみをシリアル化しようとしています。ShouldSerializeメソッドなどを使用して各プロパティをマークしたくありませんJsonDataAttribute

私がこれまでに行ったことは、LinqPadで次のように示されています

シリアル化するいくつかのサンプル クラス

class Customer
{
    public List<Order> Orders {get;set;}
    public int CustomerId {get;set;}
    public string[] Addresses {get;set;}
}

class Order
{
    public int OrderId{get;set;}
    public string Name {get;set;}
    public int Amount {get;set;}
    public Order PreviousOrder {get;set;}
}

すべてのオブジェクトをシリアル化する拡張メソッド

static class ExtensionMethods
{
    public static string JsonSerialize (this object obj)
    {
        var settings = new JsonSerializerSettings();
        settings.ContractResolver = new MyContractResolver();
        settings.DefaultValueHandling = DefaultValueHandling.Ignore;
        settings.ReferenceLoopHandling = ReferenceLoopHandling.Ignore;
        return JsonConvert.SerializeObject(obj,settings);
    }
}

カスタム コントラクト リゾルバー クラス

public class MyContractResolver: DefaultContractResolver
{
    protected override JsonProperty CreateProperty(MemberInfo member, MemberSerialization memberSerialization)
    {
        var property = base.CreateProperty(member,memberSerialization);
        property.ShouldSerialize = instance => instance.GetType().IsPrimitive || instance.GetType() == typeof(string) || instance.GetType() == typeof(decimal);
        return property;
    }
}

そして主な方法:

void Main()
{
    var customer = new Customer
                {
                    Orders = ProduceSomeOrders(),
                    Addresses = new string[] {"9450 S. Small Street Dr.","9521 Flintstone Dr. S"},
                    CustomerId = 1
                };

    var jsonOrder = customer.JsonSerialize();
    jsonOrder.Dump();
}

intdoublestring、などのサンプル タイプのみをシリアル化したいのですがdecimalbool配列、コレクション、カスタム オブジェクトなどはシリアル化しません。2 番目以降のレベルではなく、最初のレベルのみをナビゲートします。Json.Netでこれを行う簡単な方法がないのはなぜだろうか。

これは、このコードを実行したときの出力です:(空のjson)

{ }

memberこのコードを実行すると、メソッドに渡される最初のパラメーターCreatePropertyは、この場合はCustomerインスタンスであるメイン オブジェクト自体であることに気付きました。instance.GetType() == typeof(Customer)しかし、これはあらゆる種類のタイプで機能するため、メソッドで言いたくありません。この場合に期待される出力は、この場合のみCustomerIdです。

私の問題を適切に処理する方法を知っていますか?

4

2 に答える 2

3

CreatePropertyメソッドをオーバーライドする代わりに、GetSerializableObjects取得可能なすべてのメンバーを提供するため、メソッドをオーバーライドしています。

public class MyContractResolver: DefaultContractResolver
{
    protected override List<MemberInfo> GetSerializableMembers(Type objectType)
    {
        var members = base.GetSerializableMembers(objectType);
        var filteredMembers = new List<MemberInfo>();
        members.ForEach(m=>{
            if(m.MemberType == MemberTypes.Property)
            {
                PropertyInfo info = (PropertyInfo) m;
                var type = info.PropertyType;
                if(type.IsPrimitive || type == typeof(string) || type == typeof(decimal))
                {
                    filteredMembers.Add(m);
                }
            }
        });
        return filteredMembers;
    }
}
于 2013-04-10T16:35:57.900 に答える