2

I'm looking for the simplest / most elegant way to flatten a source object utilizing extension methods of the source object.

Source:

class Source
{
    public int Value1 { get; set; }
    public int Value2 { get; set; }
}

Extension method I'd like to elegantly map:

static class SourceExtensions
{
    public static int GetTotal(this Source source)
    {
        return source.Value1 + source.Value2;
    }
}

Destination:

class Destination
{
    public int Value1 { get; set; }
    public int Value2 { get; set; }
    public int Total { get; set; }
}

Is there a better way than this (one where I don't have to call out every extension method)?

using NamespaceContainingMyExtensionMethods;
...
Mapper.CreateMap<Source, Destination>()
    .ForMember(destination => destination.Total,
        opt => opt.ResolveUsing(source => source.GetTotal()));

Something like:

Mapper.CreateMap<Source, Destination>()
    .ResolveUsingExtensionsInNamespace("NamespaceContainingMyExtensionMethods");

I know I can use an inheritance heirarchy on the source objects, but in my situation, it isn't ideal.

I've researched: Does AutoMapper's convention based mappings work with LINQ extension methods? and https://github.com/AutoMapper/AutoMapper/issues/34

Community
  • 1
  • 1
Clay
  • 10,885
  • 5
  • 47
  • 44

2 Answers2

2

Added commit to my fork and make a pull request for this. Works like a charm!

commit: https://github.com/claycephus/AutoMapper/commit/e1aaf9421c63fb15daca02607d0fc3dff871fbd1

pull request: https://github.com/AutoMapper/AutoMapper/pull/221

Configure it by specifying assemblies to search:

Assembly[] extensionMethodSearch = new Assembly[] { Assembly.Load("Your.Assembly") };
Mapper.Initialize(config => config.SourceExtensionMethodSearch = extensionMethodSearch);
Mapper.CreateMap<Source, Destination>();
Clay
  • 10,885
  • 5
  • 47
  • 44
  • Since implementing this on our project, we stumbled on it several times. We're now going to get rid of it. Ever heard the saying "Too clever for its own good"? This was one of those situations. It has a tendency to produce some sneaky run-time errors as AutoMapper is very much a run-time beast, not a compile-time thing. This feature exacerbates that issue. But hopefully this is useful to someone someday. – Clay Sep 18 '12 at 21:27
0

Clay stuff is still there but it has been refactored over time. For those searching for this in automapper, you should use:

var config = new MapperConfiguration(cfg => {
    cfg.IncludeSourceExtensionMethods(typeof(SourceExtensions));
    cfg.CreateMap<Source, Destination>();
});
var mapper = config.CreateMapper();
Yepeekai
  • 2,545
  • 29
  • 22