Funq:多次注册同一对象,并使用标识符(来自会话)来解决它们

时间:2018-09-04 14:39:01

标签: c# .net servicestack funq

我目前所拥有的:

我有一个简单的string, DbContext类型的字典 我正在这样注册我的字典

container.Register<IDictionary<string, DbContext>>(x => dbContexts).ReusedWithin(ReuseScope.Request);

,然后通过简单地将字典注入我的构造函数中来再次使用字典。因此,我总是在整个字典中注入每个DbContext。稍后,我将使用存储在我的用户会话中的标识符来获取正确的DbContext。因此,使用DbContext看起来像这样:

private readonly IDictionary<string, DbContext> _dbContexts;
public FooService(IDictionary<string, DbContext> dbContexts)
{
    _dbContexts = dbContexts;
}

public void Bar()
{
    var userSession = GetSession();

    var data = _dbContexts[userSession.TargetConnectionIdentifier].Table.ToList();
}

我想要的

我只想将一个DbContext注入到我的类中。使用会话中的相同属性作为标识符。我已经看到Funq提供了使用名称注册实例的方法(例如RegisterAs<>())。但是我不太确定如何正确使用它们。

private readonly DbContext _dbContext;

public FooService(DbContext dbContext)
{
    _dbContext = dbContext;
}

我希望Funq为我自动解决正确的对象,具体取决于会话中特定属性的值。

如果有人知道答案,我将不胜感激。

1 个答案:

答案 0 :(得分:1)

IOC无权访问运行时请求上下文,因此您无法在IOC内执行此操作。

我的方法是在db上下文中注册工厂,例如:

container.Register<IDbContexts>(c => new DbContexts(dbContexts));

然后,您可以拥有一个基类,该基类提供一个帮助器来访问帮助器后面的DbContext,例如:

public class ServiceBase : Service
{
    public IDbContexts DbContexts { get; set; }

    DbContext dbContext;
    public DbContext DbContext => dbContext ?? (dbContext = DbContexts.Get(GetSession()));
}

或者如果您不需要基类,也可以使用扩展方法,例如:

public static class MyServiceExtensions
{
    public static DbContext GetDbContext(this Service service)
    {
        var dbContexts = service.TryResolve<IDbContexts>();
        return dbContexts.Get(service.GetSession());
    }
}

然后将其延迟加载到您的Service类中,例如:

DbContext dbContext;
public DbContext DbContext => dbContext ?? (dbContext = this.GetDbContext());