I am doing the following right now
container.Register<IDatabaseMapper<User>, DatabaseMapper<User, OracleException>>();
container.Register<IDatabaseMapper<Desk>, DatabaseMapper<Desk, OracleException>>();
container.Register<IDatabaseMapper<Commodity>, DatabaseMapper<Commodity, OracleException>>();
But i would like to do something like this
container.RegisterOpenGeneric(typeof(IDatabaseMapper<>), typeof(DatabaseMapper<,OracleException>));
Is this somehow possible?
Is this possible? Yes and no :-)
typeof(DatabaseMapper<,OracleException>)
is not valid C# code. You either have to supply all generic type arguments or none at all. So there is no way to inform the Container
that it should fill in the missing TException
type argument with a OracleException
. So no, you can't do this.
But yes, of course you can do this :-). Simply create a OracleExceptionDatabaseMapper<T>
class that inherits from DatabaseMapper<T, OracleException>
and use that type in the registration:
// Helper class
public class OracleExceptionDatabaseMapper<T>
: DatabaseMapper<T, OracleException>
{
}
// Registration
container.RegisterOpenGeneric(typeof(IDatabaseMapper<>),
typeof(OracleExceptionDatabaseMapper<>));
This way the given implementation has only 1 generic type and that can be mapped to the single generic type argument of the given service interface.
UPDATE
Since Simple Injector 2.4 it is possible to register parial open generic types, but since this is still not supported by C# you will have to create the partial open generic type by hand as follows:
Type databaseMapperType = typeof(DatabaseMapper<,>).MakeGenericType(
typeof(DatabaseMapper<,>).GetGenericArguments().First(),
typeof(OracleException));
container.RegisterOpenGeneric(typeof(IDatabaseMapper<>), databaseMapperType);