【问题标题】:automapper map with reflection带反射的自动映射器映射
【发布时间】:2019-08-26 08:24:17
【问题描述】:

我正在尝试创建一个自动映射器辅助函数来检查枚举的转换(我在映射器中自定义了业务逻辑)
mapper 是一个实例,非静态的。

var cfgExp = new MapperConfigurationExpression();
cfgExp.AddProfile<ProfileXXX>()
MapperConfiguration mapConfig = new MapperConfiguration(cfgExp);
IMapper mapper = new Mapper(mapConfig);
mapper.ConfigurationProvider.AssertConfigurationIsValid();
mapper.AssertEnumConversion(cfgExp);
public static void AssertEnumConversion(this IMapper @thisMapper, MapperConfigurationExpression cfgExp)
{
    try
    {
        if (@thisMapper == null)
            throw new ArgumentNullException(nameof(@thisMapper));

        List<TypePair> enumMapping = cfgExp
          .Profiles
          .SelectMany(x => x.TypeMapConfigs)
          .Where(x => x.Types.SourceType.IsEnum)
          .Select(x => x.Types)
          .ToList();


        MethodInfo methodMap = @thisMapper
            .GetType()
            .GetMethods()
            .Where(x => x.Name == "Map" && x.IsGenericMethod)
            .ToList()[0];//here i've seen 6 mappers  take first //TDestination Map<TDestination>(object source)

        foreach (var item in enumMapping)
        {
            Type tSource = item.SourceType;
            Type tDest = item.DestinationType;

            //here i've an helper to take a ienumerable<Enum>
            MethodInfo method = typeof(EnumConverters).GetMethod("GetEnumValues");
            MethodInfo methodGenericSource = method.MakeGenericMethod(tSource);
            object enumsSource = methodGenericSource.Invoke(null, null);

            IEnumerable<int> enumIenumInt = enumsSource as IEnumerable<int>;
            if (enumIenumInt == null)
                throw new ApplicationException($"enumIenumInt==null ({tSource.FullName} to {tDest.FullName})");

            Array enumArray = Array.CreateInstance(tDest, enumIenumInt.Count());
            foreach (var e in enumArray)
            {
                MethodInfo methodMapGeneric = methodMap.MakeGenericMethod(tDest);
               //here i've exeption invoking...
                methodMapGeneric.Invoke(@thisMapper, new object[1] { e });
            }
        }
    }
    catch (Exception e)
    {
        throw;
    }

但我收到异常,例如映射器未初始化... 我哪里错了!?!?

【问题讨论】:

  • 抛出了哪一行,exact 错误是什么?
  • @nvoigt methodMapGeneric.Invoke(@thisMapper, new object[1] { e });
  • 您要检查的究竟是什么?如果给定一个特定的输入枚举 A 正确的值 B 得到结果?
  • 这不是这样做的方法。检查this
  • @LucianBargaoanu 我已经在映射中做到了。现在我想要在默认 AssertConfigurationIsValid 之后有一个自定义断言

标签: .net reflection enums automapper


【解决方案1】:

我已经这样解决了

public static void AssertEnumConversion(this IMapper @thisMapper, MapperConfigurationExpression cfgExp)
{
    try
    {
        if (@thisMapper == null)
        {
            throw new ArgumentNullException(nameof(@thisMapper));
        }

        if (cfgExp == null)
        {
            throw new ArgumentNullException(nameof(cfgExp));
        }

        var profilesEnum = cfgExp
            .Profiles
            .Where(x => x.TypeMapConfigs.Any(y => y.SourceType.IsEnum))
            .Select(x => new
            {
                x.ProfileName,
                TypesEnum = x.TypeMapConfigs.Where(y => y.Types.SourceType.IsEnum).ToArray()
            })
            .ToList();

        foreach (var p in profilesEnum)
        {
            foreach (var t in p.TypesEnum)
            {
                Type tSource = t.SourceType;     //enum
                Type tDest = t.DestinationType;  //enum

                Array values = Enum.GetValues(tSource);//.Cast<E>();
                if (values == null)
                    throw new ApplicationException("values == null");

                foreach (var e in values)
                {
                    try
                    {
                        @thisMapper.Map(e, tSource, tDest);//here i need to assert conversion with automapper...
                    }
                    catch (Exception ex)
                    {
                        throw new ApplicationException($"AssertEnumConversion exception (Profile:{p.ProfileName} From:{tSource.FullName} To:{tDest.FullName} On:{e})", ex);
                    }
                } 
            }
        }
    }
    catch (Exception e)
    {
        throw;
    }
}


【讨论】:

  • 抱歉,这个@thisMapper 是做什么的?
  • 没什么特别的,只是错字或误导......在扩展方法中我通常称之为“扩展对象参数”@this
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-01-10
  • 2021-09-15
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多