我的存储库类需要从Thread.CurrentPrincipal
获取运行时值(即授权声明)以及常规单例类。
给出
public class MyRepository : IMyRepository
{
private readonly DependencyClass _dependency;
private readonly string claim;
protected MyRepository(DependencyClass _dependency, string claim)
{
//...
注册存储库时,如何注入声明? e.g。
unity.RegisterType<IMyRepository, MyRepository>(new HierarchicalLifetimeManager());
unity.RegisterType<DependencyClass>(new ContainerControlledLifetimeManager());
InjectionConstructor
似乎与构造函数参数匹配,因此导致运行时错误。我仍然更喜欢构造函数注入,我只是不确定如何做到这一点。
答案 0 :(得分:4)
我有需要运行时值的存储库类
你的DI容器应该构建包含注射剂/组分的对象图;包含应用程序逻辑的类。运行时数据不应该注入组件的构造函数中,因为这会使构造,构建和验证对象图变得复杂。
相反,应使用方法调用将运行时数据传递给对象图。这种上下文运行时数据的一般解决方案是拥有一个抽象,为其消费者提供这种上下文数据。
例如,在您的情况下,transaction-manager-ref
抽象可以解决问题:
<jpa:repositories base-package="com.foo.webapp.test.repository"
entity-manager-factory-ref="entityManagerFactory1"
transaction-manager-ref="transactionManager1" />
<jpa:repositories base-package="com.foo.webapp.repository"
entity-manager-factory-ref="entityManagerFactory2"
transaction-manager-ref="transactionManager2" />
使用这种抽象,创建一个从IClaimsContext
读取声明的实现很简单,如您所见:
public interface IClaimsContext {
string CurrentClaim { get; }
}
由于此实现不包含任何状态,因此可以将其注册为singleton而不会出现任何问题:
Thread.CurrentPrincipal
现在,public sealed class ThreadClaimsContext : IClaimsContext {
public string CurrentClaim {
get { return Thread.CurrentPrincipal... /* get claims here */; }
}
}
只能依靠unity.RegisterInstance<IClaimsContext>(new ThreadClaimsContext());
代替MyRepository
。