0

我有一个 WCF 服务,我需要从中记录对其方法的调用。为此,我使用解决方案来跟踪调用并调用我的内部审计服务,该服务使用 Entity 5.1 并使用 Ninject 注入服务/存储库/DbContext。

我的 Invoke 方法如下所示:

    public object Invoke(object instance, object[] inputs, out object[] outputs)
    {
        var methodParams = (instance).GetType().GetMethod(_operationName).GetParameters();
        var parameters = new Dictionary<string, object>();
        for (var index = 0; index < inputs.Length; index++)
            parameters.Add(methodParams[index].Name, inputs[index]);

        _auditService.TrackFilterParametersValues(_operation.Parent.Type.FullName, _operationName, _operation.Action, parameters);

        return _baseInvoker.Invoke(instance, inputs, out outputs);
    }

在我的 Ninject 模块中,我有这样注册的内部内容:

Bind<IAuditService>().To<AuditeService>().InRequestScope();
Bind(typeof(IRepository<>)).To(typeof(Repository<>)).InRequestScope();
Bind<IUnitOfWork>().To<UnitOfWork>().InRequestScope();
Bind<DbContext>().To<MyEntities>().InRequestScope();

当我在存储库中调用 dbContext 来添加新的 Audit 对象时,就会出现问题,如下所示:

_dbContext.Set<T>().Add(entity);

它错误地声称 DbContext 已被处置。

在 WCF 服务上注册 DbContext 以便为 IOperationInvoker 注册的正确方法是什么?

我不得不提一下,对于我在 MVC4 中厌倦了这个后端的主站点,我的所有这些声明都是相同的,它工作得很好(那里没有 WCF)。所以我很确定需要为 WCF 生命周期更正一些东西,但不太确定是什么。

4

2 回答 2

1

我找到了行为如此糟糕的原因:在 IOperationInvoker、IOperationBehavior 和 IServiceBehavior 形成的链中,我是通过前两个的构造函数注入 AuditService,但在最新的(IServiceBehavior)中,因为我是用它装饰 WCF 类并且不能重载构造函数,我使用 DependencyResolver 来获取具有如下属性的 AuditService:

public IAuditService AuditService
{
    get { return DependencyResolver.Current.GetService<IAuditService>();
}

然后,当我开始调试时,我注意到在 WCF 测试客户端向 WCF 查询 WSDL 数据时调用了构造函数,但从未调用过Invoke方法,因为没有调用任何 Web 方法。所以AuditService实例(和DbContext)在构造函数调用期间一切正常,但是在调用Web方法和调用IOperationInvoker的Invoke方法时,DbContext早就被释放了。

我的解决方法是从所有构造函数中删除对 AuditService 的所有引用,并将具有 DependencyResolver 的属性从 ServiceBehavior 移动到 IOperationInvoker 实现。一旦我这样做了,AuditService 就会在需要时立即被调用,以前从未如此,并且它的 DbContext 永远不会被释放。

于 2015-03-18T20:03:06.210 回答
0

如果 MyEntities 继承自 DbContext,那么这应该有效:

Bind(typeof(DbContext)).To(typeof(MyEntities)).InRequestScope();
于 2015-03-18T15:40:42.133 回答