2014-07-11 4 views
0

У меня есть следующий класс:Json.net: Как определить, находится ли свойство во время десериализации?

[DataContract] 
public class MyMessage 
{ 
    [DataMember(IsRequired = false)] 
    public string Foo { get; set; } 

    [DataMember(IsRequired = false)] 
    public string Bar { get; set; } 

    public void NotifyPropertyFound(string propName) 
    { 
     ... 
    } 

} 

Мне нужна десериализация следующего JSon входа:

{ "Foo": null, 
    "Melda": 123 
} 

Мне нужен десериализатор вызвать метод NotifyPropertyFound дважды: один раз с аргументом "Foo" (который я есть в моем классе) и еще раз с аргументом "Melda" (которого у меня нет).

Я играю с IContractResolver и JsonConverter, но ни один из них, кажется, не дает возможность вызвать метод NotifyPropertyFound. Есть идеи?

EDIT

я могу обнаружить "Foo" с помощью IValueProvider. Но мне еще нужно обнаружить "Melda".

+0

Парню, который быстро выдан голосуя, задавая этот вопрос -1, ничего не объясняя - вы действительно много помогли. Надеюсь, теперь ты счастлив. – fernacolo

ответ

0

Возможно, вы можете изменить свойство, которое будет поддерживаться частным полем вместо свойства auto. Затем вы можете попытаться вызвать этот метод в сеттере, который вызывается десериализатором по умолчанию.

Другой вариант - написать собственный десериализатор.

+1

Использование частного поля позволило бы мне обнаружить '' Foo'', но мне нужно обнаружить посторонние свойства, такие как '' Melda'' в примере. – fernacolo

+0

Это инициировано JavaScript? Если это так, вы могли бы запустить проверки в объекте javascript, прежде чем нажимать его на сервер. – TGH

+0

Спасибо, но он не инициирован JavaScript. Это API REST, который получает в качестве входного сигнала капли JSON. – fernacolo

0

Вы можете получить результат, который Вы хотите, используя пользовательские JsonConverter как следующее:

class MyMessageConverter : JsonConverter 
{ 
    public override bool CanConvert(Type objectType) 
    { 
     return (objectType == typeof(MyMessage)); 
    } 

    public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) 
    { 
     JObject jo = JObject.Load(reader); 
     MyMessage msg = jo.ToObject<MyMessage>(); 
     foreach (JProperty prop in jo.Properties()) 
     { 
      msg.NotifyPropertyFound(prop.Name); 
     } 
     return msg; 
    } 

    public override bool CanWrite 
    { 
     get { return false; } 
    } 

    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) 
    { 
     throw new NotImplementedException(); 
    } 
} 

Демо:

class Program 
{ 
    static void Main(string[] args) 
    { 
     string json = @"{ ""Foo"": null, ""Melda"": 123 }"; 

     JsonSerializerSettings settings = new JsonSerializerSettings(); 
     settings.Converters.Add(new MyMessageConverter()); 

     MyMessage msg = JsonConvert.DeserializeObject<MyMessage>(json, settings); 
    } 
} 

[DataContract] 
public class MyMessage 
{ 
    [DataMember(IsRequired = false)] 
    public string Foo { get; set; } 

    [DataMember(IsRequired = false)] 
    public string Bar { get; set; } 

    public void NotifyPropertyFound(string propName) 
    { 
     // Write to the console each time this method is called 
     Console.WriteLine(propName); 
    } 
} 

Выход:

Foo 
Melda 
Смежные вопросы