2009-02-19 94 views
7

重要;我是真的在這裏找一個StructureMap的答案。請不要說如何與溫莎,春天,團結,或任何the others使用StructureMap配置配置文件

我正在爲IoC玩StructureMap - 基本上我的目標是擁有一個定義核心類型的「默認」配置文件,以及覆蓋/擴展它的一些命名配置文件。我認爲配置文件可以做到這一點,但我根本無法通過xml或代碼API工作。特別是,如果我嘗試加載配置文件的容器:,

container = new Container(); 
container.SetDefaultsToProfile(profile); 

然後我得到「請求的配置文件(名稱)無法找到」儘管我很清楚在initialize稱爲CreateProfile(與該名稱)。

我吠叫錯了樹嗎?

(也張貼到user-group


我非常想要的是能夠定義標準(/默認) 類型,然後對各種不同的命名配置的, 覆蓋一些設置 - 也就是說,如果我有

  • 全球:IFoo =>FooIBar =>Bar
  • configA:(無變化)
  • configB:IFoo =>SpecialFoo

相信這可以映射到兩個容器中,使用命名簡檔加載。 的目的是,如果我要求無論容器爲IBar,我得到一個 Bar - 但configA返回Foo(用於IFoo),其中,作爲configB返回 SpecialFoo

有人可以給我一個線索如何配置這個? xml或 代碼都很好......我只是想讓它工作。我需要的僅僅是interface-to- 具體類型的映射(沒有特殊的配置/屬性設置)。

回答

9

訣竅是確保每個單個配置文件至少是一個在其中定義的規則。如果您不指定規則(configA),則不會創建/查看配置文件。

考慮到這些類:

public interface IFoo { string SayHello(); } 
public class Foo : IFoo { public string SayHello() { return "Hello"; } } 
public class SpecialFoo : IFoo { public string SayHello() { return "Hello Special"; } } 

public interface IBar { } 
public class Bar : IBar { } 

public interface IDummy { } 
public class Dummy : IDummy{ } 

您可以定義此註冊表:

public class MyRegistry : Registry 
{ 
    protected override void configure() 
    { 
     ForRequestedType<IBar>().TheDefault.Is.OfConcreteType<Bar>(); 
     ForRequestedType<IFoo>().TheDefault.Is.OfConcreteType<Foo>(); 
     CreateProfileNotEmpty("configA"); 
     CreateProfileNotEmpty("configB") 
      .For<IFoo>().UseConcreteType<SpecialFoo>(); 
    } 
    StructureMap.Configuration.DSL.Expressions.ProfileExpression CreateProfileNotEmpty(string profile) 
    { 
     return CreateProfile(profile) 
      .For<IDummy>().UseConcreteType<Dummy>(); 
    } 
} 

而且它會與這些測試工作:

[TestMethod] 
public void TestMethod1() 
{ 
    var container = new Container(new MyRegistry()); 
    Assert.IsNotNull(container.GetInstance<IBar>()); 
    Assert.AreEqual("Hello", container.GetInstance<IFoo>().SayHello()); 

    container.SetDefaultsToProfile("configB"); 
    Assert.IsNotNull(container.GetInstance<IBar>()); 
    Assert.AreEqual("Hello Special", container.GetInstance<IFoo>().SayHello()); 

    container.SetDefaultsToProfile("configA"); 
    Assert.IsNotNull(container.GetInstance<IBar>()); 
    Assert.AreEqual("Hello", container.GetInstance<IFoo>().SayHello()); 
} 

,如果你用簡單的CreateProfile取代CreateProfileNotEmpty ,它會在將缺省設置爲configA的行上失敗。

+1

有趣。我明天會試試。把它看作一個+1(也可能是「勝利」) - 我現在剛剛失去了選票; -p – 2009-02-25 20:19:34