首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >统一按约定注册的多接口实现

统一按约定注册的多接口实现
EN

Stack Overflow用户
提问于 2019-12-14 10:25:05
回答 1查看 283关注 0票数 0

我试图按照约定注册单个接口的多个实现,然后在其他类中使用所有这些接口作为依赖项。不幸的是,我在尝试这样做时遇到了一些困难。

我想注册多个实现,所以我添加了WithName.TypeName注册,但这似乎会导致问题。没有它,我就无法为单个接口注册多个实现。

下面是不起作用的简单例子。团结就是破例,我不知道为什么。

Unity.ResolutionFailedException:‘解析失败,错误:没有公共构造函数可用于KYPClient.IConf类型。

代码语言:javascript
运行
复制
namespace KYPClient
{
public interface IConf
{
    string conf();
}

public class Conf : IConf
{
    public string conf()
    {
        return "conf";
    }
}

public interface ILoader
{
    string load();
}

public class Load_1 : ILoader
{
    public string load()
    {
        return "load-1";
    }
}

public class Load_2 : ILoader
{
    public string load()
    {
        return "load-2";
    }
}

public class MainCls
{
    private IConf _conf;
    private IEnumerable<ILoader> _loaders;

    public MainCls(IConf conf, IEnumerable<ILoader> loaders)
    {
        _conf = conf;
        _loaders = loaders;
    }

    public void Run()
    {
        System.Console.WriteLine(_conf.conf());
        foreach (var l in _loaders)
        {
            Console.WriteLine(l.load());
        }
    }
}


internal static class Client
{
    private static void Main()
    {   
        using var container = new UnityContainer();

        container.RegisterTypes(
            AllClasses.FromAssemblies(typeof(MainCls).Assembly),
            WithMappings.FromAllInterfaces,
            WithName.TypeName,
        WithLifetime.ContainerControlled);

        var main = container.Resolve<MainCls>();

        main.Run();
    }
}

}

EN

回答 1

Stack Overflow用户

发布于 2019-12-17 23:33:28

问题是您使用的是WithName.TypeName选项。这意味着程序集中的每个类型都是作为容器中的命名注册完成的。这在您的情况下是一件好事,因为您正在注册多个ILoader实例,因此容器必须能够区分它们。但是,这也意味着当它被解析时,您必须传递名称才能让容器找到它。

换句话说,当容器看到构造函数public MainCls(IConf conf, IEnumerable<ILoader> loaders)时,它解释为“用默认名称注入IConf实例”,而这个名称并不存在于容器中。您的IConf注册名称为"Conf“(或者可能是"KYPClient.Conf",我不确定,因为我从未使用过RegisterTypes方法)。

因此,您必须在构造函数中显式地命名它。另外,每个How to configure Unity to inject an array for IEnumerable都需要一个数组来获取所有已注册的ILoader类型。

代码语言:javascript
运行
复制
public MainCls([Dependency("Conf")] IConf conf, ILoader[] loaders)

当然,使用命名依赖项也有一些缺点(例如,如果重构和重命名类会发生什么情况)。看看With Unity how do I inject a named dependency into a constructor?的第二个答案,看看使用工厂模式的策略。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/59334237

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档