I have this interface for using AutoMapper:
public interface IMapper
{
object Map(object source, Type sourceType, Type destinationType);
}
Then for each type of data, I have a different mapper class , for example:
public class UserMapper : IMapper
{
static UserMapper()
{
Mapper.CreateMap<User, UserViewModel>();
Mapper.CreateMap<UserViewModel, User>();
}
public object Map(object source, Type sourceType, Type destinationType)
{
return Mapper.Map(source, sourceType, destinationType);
}
}
Then I have IMapper as one of the parametter in my controller class like this:
public UsersController(IUsersRepository repo, IMapper userMapper)
{....}
I am using Windsor as the IOC for my application and the problem is that I want to register the components, so that when running in UsersController , it use the UserMapper class and if running on ProductsController it will use my ProductMapper class.
My registration code looks something along the line of this:
container.Register(
Component.For<IMapper>()
.ImplementedBy<UsersMapper>()
.Named("usersMapper"),
Component.For<IMapper>()
.ImplementedBy<ProductsMapper>()
.Named("productsMapper"),
Component.For<ProductController>()
.ServiceOverrides(ServiceOverride.ForKey("usersMapper").Eq("productsMapper"))
)
I have done my homework on google and stackoverflow, and i know that I need to use ServicesOverride but I am still stuck on this, could anyone give me a hand please?
Thanks
This registration works for me:
While svick's solution looks correct to me (I haven't attempted to compile it, though), this scenario is an excellent case for convention-based configuration.
Let's introduce this convention: Each consumer of IMapper will signal the intended role of the mapper by its name. By default, that name will be matched with a type of the same name - only with different casing.
So, constructor parameters could be mapped like this:
In Castle Windsor, such a configuration might look like this:
And the Sub Resolver (where the magic really happens) looks like this: