【问题标题】:StructureMap Supply string Parameter to Constructor when Requesting an InstanceStructureMap 在请求实例时向构造函数提供字符串参数
【发布时间】:2016-10-20 19:34:33
【问题描述】:

您好,在 Autofac 我可以这样做:

public class Service1_Client
{
    private const string ServiceName = "Service1";
    Func<string, RabitMqClient> _clientFunc;

    public Service1_Client(Func<string, RabitMqClient> clientFunc) 
    { 
         _clientFunc = clientFunc;
    }

    public IList<object> GetData()
    {
        return _clientFunc(this.ServiceName).Get<IList<object>>();               
    }
}

public class Service2_Client
{
    private const string ServiceName = "Service2";
    Func<string, RabitMqClient> _clientFunc;

    public Service2_Client(Func<string, RabitMqClient> clientFunc) 
    { 
         _clientFunc = clientFunc;
    }

    public IList<object> GetData()
    {
        return _clientFunc(this.ServiceName).Get<IList<object>>();               
    }
}

public class RabitMqClient
{
    private IConnectionFactory _connectionFactory;
    private string _baseServiceName;
    public RabitMqClient(IConnectionFactory connectionFactory, string baseServiceName)
    {
        _connectionFactory = connectionFactory;
        _baseServiceName = baseServiceName;
    }

    public TResult Get<TResult>()
    {
        string topicName = this.GetTopicName();
        ///Connect to the channel that uses the topic and ask for data...
    }

    private string GetTopicNAme()
    {
        /// this should be an algoritam for getting the topic from the speccified baseServiceName (I have omitted the details)
        return this._baseServiceName;
    }     
}

现在解释: 基本上我有一个依赖于 2 个参数的类(RabitMqClient):

  1. connectionFactory (IConnectionFactory)
  2. baseServiceName(字符串)

这些参数用于连接到 RabbitMq 服务器。 现在我使用 RabbitMq 中的 Topics 来多样化服务,为了得到正确的 Topic,使用了字符串参数 baseServiceName。 调用方 (Service1_Client, Service2_Client) 应提供字符串参数 baseServiceName。

在 Autofac 我可以像这样注册这个类:

builder.Register((context, parameters) =>
{
    var param = parameters.First() as Autofac.TypedParameter;
    return new HcRabbitMqClient(
        context.Resolve<IConnectionFactory>(),param.Value.ToString());
}).AsSelf().InstancePerDependency();

这告诉 Autofac,当请求这个类时,让 Autofac 解析第一个参数,但调用者将在调用站点提供第二个(字符串)参数。然后将这个字符串参数放入参数值中。 this的用法可以看上面的代码(Service1_Client,Service2_Client)GetData()方法;

如何在 StructureMap 中做到这一点?

【问题讨论】:

  • 您能否提供更多关于如何在 Autofac 的应用程序中使用它的上下文?

标签: c# dependency-injection inversion-of-control instantiation structuremap


【解决方案1】:

扩展工厂模式怎么样?

public interface IRabitMqClientFactory
{
    IRabitMqClientFactory Create(string baseServiceName);
}

public class RabitMqClientFactory : IRabitMqClientFactory
{
    public RabitMqClientFactory(IConnectionFactory connectionFactory){
        _connectionFactory = connectionFactory;
    }

    public IRabitMqClientFactory Create(string baseServiceName)
    {
        _baseServiceName = baseServiceName;
    }
}

然后简单地

public class Service1_Client
{
    private const string ServiceName = "Service1";
    private RabbitMqClient _rabbitMqClient;

    public Service1_Client(IRabitMqClientFactory rabitMqClientFactory) 
    { 
         _rabbitMqClient = rabitMqClientFactory.Create(ServiceName);
    }

    public IList<object> GetData()
    {
        return _rabbitMqClient.Get<IList<object>>();               
    }
}

它也比 IoC 中的复杂逻辑更具可读性。

【讨论】:

  • 好的,这个解决方案比我的例子更好。谢谢
【解决方案2】:

试试这个
For&lt;Func&lt;string, RabitMqClient&gt;&gt;().Use(cstr =&gt; new RabitMqClient(cstr));

【讨论】:

  • 好的,这适用于 1 个参数,但如果我有更多参数怎么办? IE。函数
  • 然后像这样添加参数For&lt;Func&lt;string, int, RabitMqClient&gt;&gt;().Use((cstr, int) =&gt; { return new RabitMqClient(cstr, int) });
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-07-05
  • 1970-01-01
  • 2019-01-21
相关资源
最近更新 更多