Upgrading AutoMapper
On more than one or two occasions now, I've found myself working with a codebase that uses AutoMapper to perform mapping between objects, most commonly to map data entity objects to their equivalent domain objects.
These codebases often are using a version of AutoMapper prior to version 4.2 which is the version that AutoMapper decided to remove it's static API. I often find the need to upgrade the version of AutoMapper that's in use for any one of a number of different reasons and so I find myself having to re-write all of the AutoMapper initialisation code as the old way of creating mappings is no longer supported.
The problem here is that, in a large enough codebase, moving from purely static mappings as was done with AutoMapper prior to v4.2 to non-static mappings that would need to be either manually constructed or injected into all of the places in the codebase that would require them. This is often a non-trivial feat and makes moving from static mappings to non-static mappings a much larger job that you might ideally like it to be.
The "proper" way to configure your AutoMaper mappings these days is write code similar to this:
var config = new MapperConfiguration(cfg => {
cfg.CreateMap<SourceObject, DestinationObject>();
});
and then to pass that config
object around, or inject it into the class that might need your mapping config. Of course, if that class is short-lived, you'll need to re-create these mapping configs again and again. Whilst this is undoubtedly the "best" approach and does not require any static objects, it's sometimes not immediately feasible in an a large, legacy codebase.
There is, however, a way of changing your old, static API-based, mapping configurations in such a way that they continue to use a static object - albeit not the same one as was in AutoMapper < v4.2 - such that the change can be a "drop-in" replacement without having a knock-on ripple effect through out the rest of the codebase.
The Old Way
So the old way of configuring AutoMapper mappings with the static API was something very similar to this:
public class AutomapperConfig
{
public static void Configure()
{
Mapper.CreateMap<SourceObjectA, DestinationObjectA>();
Mapper.CreateMap<SourceObjectB, DestinationObjectB>();
Mapper.CreateMap<SourceObjectC, DestinationObjectC>();
}
}
and the static Configure
method would be called within some entry point of your program (i.e. inside the Application_Start
method of the Global.asax.cs
class)
The New Way
And here's the new way of performing the same thing. A slight syntactical change to the code and it's a "drop-in" replacement.
public class AutomapperConfig
{
public static void Configure()
{
Mapper.Initialize(cfg =>
{
cfg.CreateMap<SourceObjectA, DestinationObjectA>();
cfg.CreateMap<SourceObjectB, DestinationObjectB>();
cfg.CreateMap<SourceObjectC, DestinationObjectC>();
}
}
}
Note how we use the new Initialize
method of the static Mapper
object passing in a lambda that performs our mapping configurations rather than constructing a new instance of the MapperConfiguration
object to pass to the relevant part of our code that needs to perform mappings.
And with that, we can easily upgrade from AutoMapper pre-v4.2 to a version post-v4.2 without the code changes being too onerous.