如何在C#/ ASP

时间:2016-11-11 08:46:08

标签: c# asp.net dependency-injection

我是来自Java世界的C#/ ASP的新手。我已经阅读了这篇文章:https://docs.asp.net/en/latest/fundamentals/dependency-injection.html#service-lifetimes-and-registration-options明智地警告了注入较小范围的依赖关系所带来的危险。不幸的是,它没有解释如何在C#/ ASP中解决这个问题。 在Java中,有一个Provider

的概念
interface Provider<T> { T get(); }

除其他外,还有助于解决范围问题: 每当某个类型T的绑定被注册时,我们就可以注入一个自动生成的Provider&lt; T&gt;的实例。而不是T然后在需要时获取T的实例:自动生成的Provider确保我们获得适合当前范围的实例(无论此范围是什么:HTTP请求,HTTP会话或其他自定义范围)。 ASP.NET核心内置的标准DI框架没有这样的东西,但我认为在C#中应该很容易实现,因为C#泛型不像java那样糟糕({{3} })。所以我创建了以下课程:

public class Provider<T>: IProvider<T> {
  private readonly IServiceProvider serviceProvider;
  public Provider(IServiceProvider serviceProvider) {
    this.serviceProvider = serviceProvider;
  }
  public T IProvider<T>.Get() {
    return serviceProvider.GetService<T>();
  }
}

我决定以下列方式使用它:

public class SingletonService : ISingletonService {
  private readonly IProvider<IScopedService> scopedServiceProvider;

  public SingletonService(IProvider<IScopedService> scopedServiceProvider) {
    this.scopedServiceProvider = scopedServiceProvider;
  }

  public string PerformMyTask() {
    var scopedDependency = scopedServiceProvider.Get();
    // do something with scopedDependency to verify we get instances
    // appropriate for the current scope
  }
}

在我的Startup课程中:

public void ConfigureServices(IServiceCollection services) {
  services.AddSingleton<ISingletonService, SingletonService>();
  services.AddScoped<IScopedService, ScopedService>();
  services.AddTransient<IProvider<IScopedService>, Provider<IScopedService>>();
  // other bindings here
}

不幸的是,这并不像我预期的那样工作,因为IServiceProvider实例似乎也限定为当前的HTTP请求,并且在处理不同的请求期间,我从提供者那里获得了完全相同的ScopedDependency实例:(

任何提示如何解决此问题? 是否有更高级别的&#34;对象比ServiceProvider可能大致绑定到应用程序生命周期(而不是当前请求),它创建了我可以注入到我的Provider对象而不是ServiceProvider的请求范围对象(或ServiceProvider本身)的实例?例如,在Java中,如果我使用google Guice作为DI框架,则会有一个Injector对象,通常在应用程序启动时创建,该应用程序包含所有类型绑定并具有方法

<T> T getInstance(Class<T> type);

检查当前范围是什么并返回相应的实例。

修改

我认为一种可行的方法是每次在Proivder&lt; T&gt; .Get()方法中获取对ServiceProvider实例的新引用,而不是在构造函数中注入并存储为实例var。这样,我的组件仍然不会被对框架特定的IServiceProvider的引用污染,因为它将在Provider&lt; T&gt;的实现中隐藏它们。他们通过抽象IProvider访问&lt; T&gt;接口。但我无法在网上找到可以从我的Provider类获得此类引用以及如何执行此操作的内容。任何指向这个方向的人都会受到赞赏:)

谢谢!

1 个答案:

答案 0 :(得分:1)

好的,发现它:

.each()

并在初创公司:

$(document).ready(function () {
     $(".cardcont img").each(function(){              
            $(this).click(function(){
                if($(this).hasClass('active')){
                    $(this).removeClass('active');
                  $(this).css({"transform": "translate3d(0px, 0px, 0px)"});
                }else{
                  $(".cardcont img").css({"transform": "translate3d(0px, 0px, 0px)"});
                  $(this).css({"transform": "translate3d(-100px, 0px, 0px)"});
                  $(this).addClass('active');                
                }
            });            
     });
});

:)

有关使用和注册HttpContextAccessor

的更多详细信息,请参阅https://github.com/aspnet/Hosting/issues/793