0

I'm trying to implement a TypeConverter for a custom Node class of mine. (I was led to this approach by the answer to this question.) In my class NodeConverter : TypeConverter, I have the following:

public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
{
    if (sourceType == typeof(string))
    {
        return true;
    }

    return base.CanConvertFrom(context, sourceType);
}

public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value)
{
    if (value is string)
    {
        // parse the string, return a new node
    }

    return base.ConvertFrom(context, culture, value);
}

I've also added [TypeConverter(typeof(NodeConverter))] as an attribute to my Node class. Then in a unit test I have the following:

var str = "{\"Username\":\"123\",\"Name\":\"Test Name\",\"Degree\":0}";
var deserialized = JsonConvert.DeserializeObject<Node>(str);

When I run the unit test, I get this error:

Newtonsoft.Json.JsonSerializationException: 'Cannot deserialize the current JSON object (e.g. {"name":"value"}) into type 'd3js.Shared.Graph.Node' because the type requires a JSON string value to deserialize correctly.

It's not clear to me what a "JSON string value" is, or how it differs from what I'm using here, so I'm unsure how to proceed.

ProgrammingLlama
  • 36,677
  • 7
  • 67
  • 86
user3678429
  • 258
  • 1
  • 3
  • 9
  • Probably a duplicate of [Newtonsoft.JSON cannot convert model with TypeConverter attribute](https://stackoverflow.com/q/31325866/3744182), agree? – dbc Nov 19 '18 at 03:48
  • I read that one, but I thought that the problem there is that the user is trying to call JsonConvert from within their TypeConverter, which produces a circularity, whereas I am not. (The "parse" comment in my code snippet glosses a bunch of code I wrote that does not reference anything else.) – user3678429 Nov 19 '18 at 04:03
  • There are a few things going on in that answer. The most relevant statement is, *Json.NET will try to use a `TypeConverter` if one is present to convert a class to be serialized to a JSON string.* The string you are trying to deserialize contains a JSON object, not a JSON string primitive, which is what Json.NET expects now that you have applied the type converter. Applying `NoTypeConverterJsonConverter` from that answer should resolve the problem. – dbc Nov 19 '18 at 04:11
  • I applied your solution successfully before submitting this question, but went ahead because I thought it might not be necessary (again, because I thought that circularity was the real problem with the previous question). Is the suggestion here that Json.NET expects a string primitive for any TypeConverter, regardless of how it is actually implemented? Or is there something about my TypeConverter in particular that determines that? In any case, thanks for your help. – user3678429 Nov 19 '18 at 04:26
  • Json.NET expects a string primitive whenever a type converter is applied. See [Serialization Guide](https://www.newtonsoft.com/json/help/html/serializationguide.htm) which states that *TypeConverter (convertible to String)* maps to a JSON primitive string. – dbc Nov 19 '18 at 04:31
  • Why do you need a TypeConverter for your Node class? What is the real problem you are trying to solve here? You said you were led here from a question asking how to make a complex key to a dictionary, but that doesn't look like what you are doing in the above unit test code. Can you give us some background? Maybe a TypeConverter isn't the right solution. – Brian Rogers Nov 19 '18 at 05:12

0 Answers0