简体   繁体   中英

TypeConverter isn't found for property

This is basically a continuation of the question: Typeconverter not working for single properties

The original question was not marked answered, but it seemed to be the way forward for a particular scenario in my project especially since all my reading suggests it should really work. I gave it a shot, but came up with the same problem as mentioned in the final comment (no breakpoints are hit or, in my case, no output dumped to the results window). Here's what I'm starting with, stripped down to a basic example for my needs†.

In LINQPad

void Main()
{
    var prop = typeof(Request).GetProperty("Names");
    var converter = TypeDescriptor.GetConverter(prop.PropertyType.Dump()).Dump();
    var value = converter.ConvertFrom("One,Two").Dump();
}

public class Request
{
    [TypeConverter(typeof(EnumerableTypeConverter<string>))]
    public IEnumerable<string> Names { get; set; }
}

public class EnumerableTypeConverter<T> : TypeConverter
{
    public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
    {
        new { Context = context, SourceType = sourceType }.Dump("CanConvertFrom");

        if (sourceType == typeof(string))
            return true;

        return false;
    }

    public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType)
    {
        new { Context = context, DestinationType = destinationType }.Dump("CanConvertTo");

        return true;
    }

    public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value)
    {
        new { Context = context, Culture = culture, Value = value }.Dump("ConvertFrom");

        var source = value as string;

        if (source == null)
            return value.ToString();

        return source;
    }

    public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType)
    {
        new { Context = context, Culture = culture, Value = value, DestinationType = destinationType }.Dump("ConvertTo");

        var s = value as IEnumerable<string>;

        return s != null ? string.Join(",", s) : base.ConvertFrom(context, culture, value);
    }

    public override bool IsValid(ITypeDescriptorContext context, object value)
    {
        new { Context = context, Value = value }.Dump("IsValid");

        return true;
    }
}

The output is

typeof(IEnumerable<String>)
System.Collections.Generic.IEnumerable`1[System.String]

ReferenceConverter
System.ComponentModel.ReferenceConverter

null

This suggests the problem is one of 1) it isn't seeing the TypeConverterAttribute definition, 2) it isn't finding my custom TypeConverter , or 3) it can't create it and silently fails. All of them seem unlikely, but clearly the result doesn't lie. Thus, something in my understanding is amiss. When I directly instantiated an instance, I did not encounter any exceptions.

var testConverter = new EnumerableTypeConverter<string>().Dump();

EnumerableTypeConverter<String>
UserQuery+EnumerableTypeConverter`1[System.String]

For grins and giggles, I tried the non-generic approach

[TypeConverter(typeof(EnumerableStringConverter))]
public IEnumerable<string> Names { get; set; }

public class EnumerableStringConverter : TypeConverter
{
    // -- same implementation as EnumerableTypeConverter<T> --
}

but received the same outcome. What am I missing here?


† The code will read through a file containing property names and associated values. Next it will look for the matching property by name and set the value via the converter. Some of the real values are JSON arrays, but I was taking small steps to validate what I was doing prior to creating the full solution of returning a deserialized JSON array into the matching property.

You set converter to the property therefore you should get converter for this property not for type IEnumerable<string> .

static void Main(string[] args)
{
    var properties = TypeDescriptor.GetProperties(typeof(Request));
    var propItem = properties["Names"];
    var converter = propItem.Converter;
    // converter has type {EnumerableTypeConverter<string>}
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM