我有一个现有的ASP.NET MVC应用程序,并使用StructureMap作为我选择的IOC容器。目前,当控制器需要IMembershipProvider时,我使用StructureMap根据我的web.config文件中的BuyerMembershipProvider配置在控制器的构造函数中注入一个具体实例,如下面的解决方案代码所示:
ObjectFactory.Initialize(x =>
{
x.ForRequestedType<IMembershipService>().TheDefaultIsConcreteType<AccountMembershipService>();
x.ForRequestedType<IFormsAuthentication>().TheDefaultIsConcreteType<FormsAuthenticationService>();
x.ForRequestedType<MembershipProvider>().TheDefault.IsThis(SecurityProvider.Providers["BuyerMembershipProvider"]);
});
这很好用。但是,它绑定到“买方”用户类型。卖方信息存储在不同的数据库中,并具有不同的表来存储成员资格信息。基本上,我希望能够根据上下文注入BuyerMembershipProvider或SellerMembership Provider,并在我的objectfactory初始化中具有以下内容:
x.ForRequestedType<MembershipProvider>().TheDefault.IsThis(SecurityProvider.Providers["BuyerMembershipProvider"]);
x.ForRequestedType<MembershipProvider>().TheDefault.IsThis(SecurityProvider.Providers["SellerMembershipProvider"]);
初始化objectfactory时是否可以在两个具体实现之间做出决定?
非常感谢任何帮助, 提前致谢! JP
答案 0 :(得分:2)
您可以定义一个工厂lambda表达式,它将在运行时决定。
var securityProviderName = ConfigurationManager.AppSettings["securityProvider"];
bool requireBuyerProvider = (securityProviderName == "Buyer");
ObjectFactory.Initialize(x =>
{
x.For<MembershipProvider>().Use(c=>
{
if (requireBuyerProvider)
c.GetInstance<SellerMemberShipProvider>();
else
c.GetInstance<BuyerMembershipProvider>();
});
});
答案 1 :(得分:1)
在不同实现之间进行选择的主要机制是通过
您不能为给定类型声明2个默认值(这应该是显而易见的),但您可以命名一个实例并说明您希望在何种情况下使用它。
定义一个命名实例,例如像这样:
InstanceOf<IApplicationModule>()
.Is.OfConcreteType<BusinessProcessSupport>()
.WithName("BusinessProcessSupport");
以下是一个使用命名实例来实现某个ctor依赖关系的示例:
ForRequestedType<MenuStripModule>()
.CacheBy(InstanceScope.Singleton)
.TheDefault.Is.OfConcreteType<MenuStripModule>()
.CtorDependency<ICommandInfoProvider>()
.Is(i => i.TheInstanceNamed("Functions"));
最后你可以看一下使用条件功能的(有点讨厌的)StructureMap表达式:http://realfiction.net/Content/Entry/142 请注意您使用的是StructureMap 2.5。*语法。 2.6。* out已经修改了配置语法,使其更加简明扼要。