2016-08-02 142 views
2

我試圖在我的軟件上實現從核心的依賴注入,以取代Ninject並更新所有新技術。MVC上的依賴注入問題

順便說一句,我在通用的一些接口上遇到問題。對於這種情況,我直接獲得一個Exception,注入器無法創建我的類的實例。

我插在樣本案例的一小段代碼上面,使我着火。

​​

這樣正確嗎?我怎樣才能做到這一點?

類實現:

public class MyRepository<TEntity, TContext> : IRepositoryBase 
    where TEntity : class 
    where TContext : IDbContext, new() 
{ 
... 
} 

接口:

public interface IRepository : IDisposable 
{ 
... 
} 

謝謝!

+0

這裏是我正在做我的核心庫的DependencyInjection:services.AddScoped (); – lucas

+0

你(lucas)和OP之間有明顯的區別。請注意開放式泛型。你仍然在覈心中使用DI框架,核心只是公開一些接口來輕鬆掛接它。 –

+0

我仍然會繼續刪除Ninject,並添加諸如Autofac,StructureMap或LightInject之類的東西。但是,該文檔指出,功能非常有限,我認爲這不會延伸到開放泛型。我喜歡結構映射,因爲它是基於約定的程序集掃描 –

回答

0

我結束了使用Autofac並沒有任何變化我的結構每一個事情再次開始工作。

將等待多一點文件和更多的人使用,所以我可以改變我的實施使用MS DI。

5

這並沒有什麼意義。你會問容器IRepository,那麼它如何知道泛型類型參數應該是什麼樣的,以便它能給你一個MyRepository<,>

所以當要求返回這樣一個對象:

public class MyService 
{ 
    private IRepository<Something, SomethingElse> _repo; 

    public MyService(IRepository<Something, SomethingElse> repo) 
    { 
     // Container will actually give us MyRepository<Something, SomethingElse> 
     _repo = repo; 
    } 
} 

我希望之一:

services.AddTransient(typeof(IRepository<,>), typeof(MyRepository<,>)); 

,或者,如果你的資料​​庫不需要是通用的(我不知道了解爲什麼它會需要通用參數,因爲它是),那麼我會想到這一點:

services.AddTransient(typeof(IRepository), typeof(MyRepository)); 

然而,由於沒有這裏涉及到仿製藥,你可以用另一種形式來實現同樣的事情少打字:

services.AddTransient<IRepository, MyRepository>(); 

所以,真正的答案是解決你的接口/類設計。顯示更多的執行他們會有所幫助。

UPDATE

你的執行工作必須:

類實現:

public class MyRepository<TEntity, TContext> : IRepository<TEntity, TContext> 
    where TEntity : class 
    where TContext : IDbContext, new() 
{ 
... 
} 

接口:

public interface IRepository<TEntity, TContext> : IDisposable 
    where TEntity : class 
    where TContext : IDbContext, new() 
{ 
... 
} 
+0

我同意你的看法,但只有在部分內容中,我的實現才真正接受並且合理。我用更多的代碼更新了我的問題。 –

+0

對不起,沒有幫助。你所顯示的內容在C#中不起作用。你的類與界面沒有任何關係,所以沒有容器可以爲你做到這一點。此外,通常抽象類不是具有「基本」後綴約定,而不是接口(而是具有「I」前綴)。 –

+0

這真的起作用,所以在Ninject和Autofac上工作,問題僅在於Microsoft的DI不接受泛型 –

0

註冊所有倉庫使用:

 var allRepositories = GetType().GetTypeInfo() 
     .Assembly.GetTypes().Where(p => 
      p.GetTypeInfo().IsClass && 
      !p.GetTypeInfo().IsAbstract && 
      typeof(IRepository).IsAssignableFrom(p)); 
     foreach (var repo in allRepositories) 
     { 
      var allInterfaces = repo .GetInterfaces(); 
      var mainInterfaces = allInterfaces.Except 
        (allInterfaces.SelectMany(t => t.GetInterfaces())); 
      foreach (var itype in mainInterfaces) 
      { 
       services.AddScoped(itype, repo); 
      } 
     } 

然後解決它:

public YourClass(IRepository<T> repo) 
{ 
    //... 
} 
+0

我的代碼幾乎就是這樣,問題不是所有的註冊,但只有當它是一個通用的接口,引發我的臉上的異常。無論如何,感謝您的幫助 –

+0

我有一個類似的scenerio。我有IValidator (繼承自IValidator)通用接口和此接口的實現。這個對我有用。 –

+0

好吧,讓我再試一次。 –