0

I have a contract whose json may or may not be in correct shape. The contract is this:

class TestContract
{
    string TestString1;
    string TestString2;
}

The json usually looks like this:

{ "TestString1": "Test", "TestString2": "Test" }

But it could look like this:

{ "TestString1": "Test", "TestString2":{ "Field": "Test" } }

The second case means something has gone wrong, but I do not want to throw an exception. I want to log that there is an issue, ignore TestString2 and proceed with the serialization.

In this case the resulting object should be the same as the one from this json string:

{ "TestString1": "Test" }

However, this seemingly cannot be handled with regular error handling (https://www.newtonsoft.com/json/help/html/SerializationErrorHandling.htm), because the error propagates up and the entire resulting object is null.

I don't see a reason why this shouldn't be able to be done, because the json is valid, just represents a slightly different object than the one I am deserializing into, just the same way as if you handle the error of trying to cast a string into an int. But I can't find any way to handle this. I saw a suggestion for using JsonReader, but it doesn't seem this can work as a generic solution. I need the error handling to take place no matter how complex the class and object are.

Anyone ever tried this before?

  • 1
    You can make a custom `JsonConverter` for your `TestString2` property which will handle the string but return null if the JSON contains an object instead. See [How to deserialize a JSON property that can be two different data types using Json.NET](https://stackoverflow.com/q/20432166/10263) for a similar example. – Brian Rogers Oct 20 '20 at 22:56
  • Another similar question, in which a value could be a string or an object, and a `JsonConverter` is used to deserialize it: [Deserialize a value serialized in two different ways with Json.Net](https://stackoverflow.com/q/49846209/3744182). Do either of the above two questions answer yours also? – dbc Oct 21 '20 at 00:17
  • Unfortunately I cannot make a custom converter here. This is a templated method that will be called by any number of callers with any contract. The whole idea here is this is entirely generic. this code doesn't know the json or the contract form. We basically want to deserialize it into fields that we can, but ignore ones that do not. Again these are error cases, we don't expect this to happen, but if some part of the json doesn't match the contract, we still want to retrieve as much of the data as possible. – Luke Holbert Oct 22 '20 at 00:01

0 Answers0