2

我想在城堡 xml 配置文件中执行此代码等效项。

// Foo(字符串名称)

IFoo f = new Foo(StaticBarClass.Name);




XML

现在对于 XML,我知道除了参数部分中的东西之外的所有内容(例如,等等)。

参数部分会是什么样子?

<component id="blah"
           service="blah"
           type="blah">
  <parameters>
    <name>StaticBarClas.Name_THAT_I_NEED_HELP_WITH</name>
  </parameters>
4

2 回答 2

1

您可以使用的一种方法是用您自己的变体替换配置参数检查器,这可以引入一些额外的行为 - 这是一个快速原型:

public class ExtendedConfigurationParametersInspector : IContributeComponentModelConstruction
{
  #region IContributeComponentModelConstruction Members

  public virtual void ProcessModel(IKernel kernel, ComponentModel model)
  {
    if (model.Configuration == null) return;

    IConfiguration parameters = model.Configuration.Children["parameters"];

    if (parameters == null) return;

    foreach (IConfiguration parameter in parameters.Children)
    {
      String name = parameter.Name;
      String value = parameter.Value;

      if (value == null && parameter.Children.Count != 0)
      {
        IConfiguration parameterValue = parameter.Children[0];
        model.Parameters.Add(name, parameterValue);
      }
      else
      {
        if (parameter.Attributes["type"] == "static")
        {
          int lastIndex = parameter.Value.LastIndexOf(".");
          string typeName = parameter.Value.Substring(0, lastIndex);
          string field = parameter.Value.Substring(lastIndex + 1);
          Type ownerType = Type.GetType(typeName);
          FieldInfo valueField = ownerType.GetField(field);
          value = (string) valueField.GetValue(null);
        }

        model.Parameters.Add(name, value);
      }
    }

    foreach (ParameterModel parameter in model.Parameters)
    {
      if (parameter.Value == null || !ReferenceExpressionUtil.IsReference(parameter.Value))
      {
        continue;
      }

      String newKey = ReferenceExpressionUtil.ExtractComponentKey(parameter.Value);

      model.Dependencies.Add(new DependencyModel(DependencyType.ServiceOverride, newKey, null, false));
    }
  }

  #endregion
}

public class ExtendedComponentBuilder : DefaultComponentModelBuilder
{
  public ExtendedComponentBuilder(IKernel kernel) : base(kernel)
  {
  }

  protected override void InitializeContributors()
  {
    AddContributor(new GenericInspector());
    AddContributor(new ConfigurationModelInspector());
    AddContributor(new ExtendedConfigurationParametersInspector());
    AddContributor(new LifestyleModelInspector());
    AddContributor(new ConstructorDependenciesModelInspector());
    AddContributor(new PropertiesDependenciesModelInspector());
    AddContributor(new LifecycleModelInspector());
    AddContributor(new InterceptorInspector());
    AddContributor(new ComponentActivatorInspector());
    AddContributor(new ComponentProxyInspector());
  }
}

public class ExtendedWindsorContainer : WindsorContainer
{
  public ExtendedWindsorContainer(IConfigurationInterpreter interpreter)
    : base(CreateKernel(), new Castle.Windsor.Installer.DefaultComponentInstaller())
  {
    if (interpreter == null) throw new ArgumentNullException("interpreter");

    interpreter.ProcessResource(interpreter.Source, Kernel.ConfigurationStore);

    RunInstaller();
  }

  private static IKernel CreateKernel()
  {
    DefaultKernel kernel = new DefaultKernel();
    kernel.ComponentModelBuilder = new ExtendedComponentBuilder(kernel);
    return kernel;
  }
}

然后,您可以像这样连接容器中的属性,其中为参数指定“静态”类型将导致值被参数值引用的静态字段替换。

<castle>
  <components>
    <component id="test"
           type="SomeNamespace.TestComponent,Example">
      <parameters>
        <value type="static">SomeNamespace.SomeClass.TheStaticFieldValue</value>
      </parameters>
    </component>
  </components>
</castle>

不幸的是,由于组件模型中的参数是不可变的,因此您通常无法通过更简单的方式(例如模型创建内核事件)来执行此操作。

于 2008-12-21T11:00:45.527 回答
1

您不能单独从 xml 进行设置。但是您可以使用工厂设施来执行此操作。

于 2008-12-19T19:20:11.307 回答