AutoMapper.Extensions.EnumMapping
The built-in enum mapper is not configurable, it can only be replaced. Alternatively, AutoMapper supports convention based mapping of enum values in a separate package AutoMapper.Extensions.EnumMapping.
Usage
For method CreateMap
this library provide a ConvertUsingEnumMapping
method. This method add all default mappings from source to destination enum values.
If you want to change some mappings, then you can use MapValue
method. This is a chainable method.
Default the enum values are mapped by value (explicitly: MapByValue()
), but it is possible to map by name calling MapByName()
.
using AutoMapper.Extensions.EnumMapping;
public enum Source
{
Default = 0,
First = 1,
Second = 2
}
public enum Destination
{
Default = 0,
Second = 2
}
internal class YourProfile : Profile
{
public YourProfile()
{
CreateMap<Source, Destination>()
.ConvertUsingEnumMapping(opt => opt
// optional: .MapByValue() or MapByName(), without configuration MapByValue is used
.MapValue(Source.First, Destination.Default)
)
.ReverseMap(); // to support Destination to Source mapping, including custom mappings of ConvertUsingEnumMapping
}
}
...
Default Convention
The package AutoMapper.Extensions.EnumMapping will map all values from Source type to Destination type if both enum types have the same value (or by name or by value). All Source enum values which have no Target equivalent, will throw an exception if EnumMappingValidation is enabled.
ReverseMap Convention
For method ReverseMap
the same convention is used as for default mappings, but it also respects override enum value mappings if possible.
The following steps determines the reversed overrides:
Create mappings for
Source
toDestination
(default convention), including custom overrides.Create mappings for
Destination
toSource
(default convention), without custom overrides (must be determined)The mappings from step 1 will be used to determine the overrides for the
ReverseMap
. Therefore the mappings are grouped byDestination
value.3a) if there is a matching `Source` value for the `Destination` value, then that mapping is preferred and no override is needed
It is possible that a
Destination
value has multipleSource
values specified by override mappings.We have to determine which
Source
value will be the newDestination
for the currentDestination
value (which is the newSource
value)For every
Source
value per groupedDestination
value:3b) if the `Source` enum value does not exists in the `Destination` enum type, then that mapping cannot reversed 3c) if there is a `Source` value which is not a `Destination` part of the mappings from step 1, then that mapping cannot reversed 3d) if the `Source` value is not excluded by option b and c, the that `Source` value is the new `Destination` value.
All overrides which are determined in step 3 will be applied to mappings from step 2.
Finally, the custom mappings provided to method
ReverseMap
will be applied.
Testing
AutoMapper provides a nice tooling for validating typemaps. This package adds an extra EnumMapperConfigurationExpressionExtensions.EnableEnumMappingValidation
extension method to extend the existing AssertConfigurationIsValid()
method to validate also the enum mappings.
To enable testing the enum mapping configuration:
public class MappingConfigurationsTests
{
[Fact]
public void WhenProfilesAreConfigured_ItShouldNotThrowException()
{
// Arrange
var config = new MapperConfiguration(configuration =>
{
configuration.EnableEnumMappingValidation();
configuration.AddMaps(typeof(AssemblyInfo).GetTypeInfo().Assembly);
});
// Assert
config.AssertConfigurationIsValid();
}
}