UNITY:每次传递一个新的datacontext?

mar*_*ith 5 datacontext dependency-injection ioc-container unity-container linq-to-sql

我试图使用unity每次使用一个新实例自动在我的存储库中注入一个datacontext ..我的想法是确保每次注入一个新的datacontext

目前它无法创建存储库,我认为它无法解析MyDataContext

在"存储库"(见下文)上创建构造函数之前,在我的存储库中接收DataContext一切正常但现在它失败了..

我目前在我的unity容器中有这个设置,我在global.asax中创建,我也注册了MyDataContext类型,这是标准的DataContext

        container = new UnityContainer();

        Container.RegisterType<MyDataContext, MyDataContext>()
            .RegisterType<IOfficeRepository, OfficeRepository>()
            .RegisterType<IOfficeService, OfficeService>();
Run Code Online (Sandbox Code Playgroud)

基本上我有一个像这样调用存储库的服务

public class OfficeService : IOfficeService
{

    IOfficeRepository repository = null;

    public OfficeService(IOfficeRepository repository)
    {
        this.repository = repository;

        if (this.repository == null)
            throw new InvalidOperationException("Repository cannot be null");
    }
Run Code Online (Sandbox Code Playgroud)

这是我的存储库

public class OfficeRepository : IOfficeRepository
{
    private MyDataContext db;

    public OfficeRepository (MyDataContext dataContext)
    {
        this.db = dataContext;
    }
Run Code Online (Sandbox Code Playgroud)

编辑

我差点忘了我这样做是为了创建服务

officeService = Bootstrapper.Container.Resolve<IOfficeService>();
Run Code Online (Sandbox Code Playgroud)

编辑 - 生成的错误

 Resolution of the dependency failed, type = "MarkSmith.IOfficeService", name = "".
 Exception message is: The current build operation (build key Build 
 Key[MarkSmith.OfficeService, null]) failed: The parameter repository could not be 
 resolved when attempting to call constructor 
 MarkSmith.OfficeService(MarkSmith.IOfficeRepository repository). (Strategy type BuildPlanStrategy, index 3)
Run Code Online (Sandbox Code Playgroud)

编辑 - 删除存储库工作的构造函数

这与datacontext有关,因为如果我删除存储库上的构造函数,它接受一个DataContext然后一切正常,但当然我需要它接受一个DataContext,每次都能注入一个"NEW"datacontext

public class OfficeRepository : IOfficeRepository
{
    private MyDataContext db new MyDataContext(); // CHANGE

    //public OfficeRepository (MyDataContext dataContext)
    //{
        //this.db = dataContext;
    //}
Run Code Online (Sandbox Code Playgroud)

编辑 - 实际错误

深挖后我发现了这个错误....

The type MyDataContext has multiple constructors of length 2. 
Unable to disambiguate. (Strategy type DynamicMethodConstructorStrategy, index 0)
(Strategy type BuildPlanStrategy, index 3)
Run Code Online (Sandbox Code Playgroud)

编辑 - 用1行代码重新测试DATACONTEXT的测试

这也失败了与上面相同的错误 - 多个构造函数

  MyDataContext test = Bootstrapper.Container.Resolve<MyDataContext >();
Run Code Online (Sandbox Code Playgroud)

编辑 - 我的DATACONTEXT上的所有结构

这些是由exernal util创建的,但一切都应该很好..

    [System.Diagnostics.DebuggerNonUserCode]
    public MyDataContext()
        : base(ConnectionString, mappingCache)
    {
        OnCreated();
    }

    [System.Diagnostics.DebuggerNonUserCode]
    public MyDataContext(string connection)
        : base(connection, mappingCache)
    {
        OnCreated();
    }

    [System.Diagnostics.DebuggerNonUserCode]
    public MyDataContext(System.Data.IDbConnection connection)
        : base(connection, mappingCache)
    {
        OnCreated();
    }

    [System.Diagnostics.DebuggerNonUserCode]
    public MyDataContext(string connection, System.Data.Linq.Mapping.MappingSource mappingSource)
        : base(connection, mappingSource)
    {
        OnCreated();
    }

    [System.Diagnostics.DebuggerNonUserCode]
    public MyDataContext(System.Data.IDbConnection connection, System.Data.Linq.Mapping.MappingSource mappingSource)
        : base(connection, mappingSource)
    {
        OnCreated();
    }
Run Code Online (Sandbox Code Playgroud)

编辑 - 演示在没有Unity的情况下在代码中创建DataContext 100%没有问题

   MyDataContext tes2t = new MyDataContext ();
Run Code Online (Sandbox Code Playgroud)

Mar*_*ann 10

我不确定这是否有效,但您是否尝试将MyDataContext注册为组件而不是类型映射?

container.RegisterType<MyDataContext>();
Run Code Online (Sandbox Code Playgroud)

代替

container.RegisterType<MyDataContext, MyDataContext>();
Run Code Online (Sandbox Code Playgroud)

编辑基于新信息

罪魁祸首似乎是MyDataContext有多个构造函数.这是大多数DI容器的常见问题,因为它们只需要选择和使用一个.如果您可以通过将MyDataContext限制为只有一个构造函数来消除歧义,那么这可能是最简单的解决方案.

否则,您应该能够在注册存储库时使用InjectionConstructor实例来标识构造函数.假设您要使用以连接字符串作为参数的构造函数:

string connectionString =
    ConfigurationManager.ConnectionStrings["MyConnection"].ConnectionString;
var injectedConnectionString = new InjectionConstructor(connectionString);
container.RegisterType<MyDataContext>(injectedConnectionString);
Run Code Online (Sandbox Code Playgroud)