Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/271.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 使用Autofac创建可以返回不同SQL引擎的工厂_C#_Dependency Injection_Autofac - Fatal编程技术网

C# 使用Autofac创建可以返回不同SQL引擎的工厂

C# 使用Autofac创建可以返回不同SQL引擎的工厂,c#,dependency-injection,autofac,C#,Dependency Injection,Autofac,我正在尝试重构一个现有的解决方案,它不是为了使用DI和Autofac而编写的,并且遇到了一些问题。该解决方案支持多种SQL数据库类型MSSQL、MySQL、PostgreSQL等,用户可以在应用ie中连接多种不同类型的数据库。它们可能同时连接MSSQL和PostgreSQL数据库。当DB连接到应用程序时,类型存储在枚举中。在有问题的DBs上执行操作时,它当前使用以下静态工厂返回数据层: public static class DatabaseFactoryController { pub

我正在尝试重构一个现有的解决方案,它不是为了使用DI和Autofac而编写的,并且遇到了一些问题。该解决方案支持多种SQL数据库类型MSSQL、MySQL、PostgreSQL等,用户可以在应用ie中连接多种不同类型的数据库。它们可能同时连接MSSQL和PostgreSQL数据库。当DB连接到应用程序时,类型存储在枚举中。在有问题的DBs上执行操作时,它当前使用以下静态工厂返回数据层:

public static class DatabaseFactoryController
{
    public static IDatalayer GetDatalayer(ConnType databaseType)
    {
        switch (databaseType)
        {
            case ConnType.Mssql:
                return new MssqlModel());
            case ConnType.Postgre:
                return new PostgreModel());
            case ConnType.MySql:
                return new MysqlModel());
            default:
                throw new ArgumentOutOfRangeException(nameof(databaseType));
        }
    }
}
现在的问题是代码中的其他控制器需要为用户当前访问的DB注入适当的数据层,例如:

public class SizeController : IDataController
{
    private readonly IDatalayer _datalayer;

    public SizeController(IDatalayer datalayer)
    {
        _datalayer = datalayer;
    }

    public Response<SizeInfo> GetData(IRequest request)
    {
        <actions taken here using datalayer>
    }
}
但是,我如何连接Autofac以在控制器中动态注入正确的数据层,对于为控制器的任何给定调用实例化选择的DB,而无需转到ServiceLocator。我很确定这是可能的,但我对Autofac还很陌生,所以也许这就是为什么我不能根据文档使它工作的原因。我试过这样做:


但在该实现中,我看不到如何在运行时选择要注入构造函数的实现。也许我遗漏了一些非常明显的东西,或者我需要从根本上重构代码。任何输入都将被重视,因为我已经在这个问题上纠缠了一段时间。

正如您使用的文章所示

public class SizeController : IDataController
{
    private readonly IDatalayer _datalayer;

    public SizeController(Func<ConnType, IDatalayer> dataLayerFactory)
    {
        _datalayer = dataLayerFactory(ConnType.Mssql);
    }

    public Response<SizeInfo> GetData(IRequest request)
    {
        //<actions taken here using datalayer>
        _datalayer.SomeIDatalayerMethod();
    }
}

在这种情况下,他们可能同时连接了MSSQL和PostgreSQL数据库,应该选择哪个IDatalayer?MS one还是Postgres one?有请求类型的那个,但我想我现在看到了下面给出的Aleksey的答案。我必须在运行时将ConnType作为参数传入,然后它才能选择正确的实现。谢谢。最后我做了类似的事情,除了存储Func并将ConnType作为GetData方法的参数,以确保每次调用都获得了正确的数据层。
public class SizeController : IDataController
{
    private readonly IDatalayer _datalayer;

    public SizeController(Func<ConnType, IDatalayer> dataLayerFactory)
    {
        _datalayer = dataLayerFactory(ConnType.Mssql);
    }

    public Response<SizeInfo> GetData(IRequest request)
    {
        //<actions taken here using datalayer>
        _datalayer.SomeIDatalayerMethod();
    }
}