2016-06-22 3 views
1

Я использую FluentNHibernate и Unity для использования в моем asp.net webapi. Я использую шаблон работы для настройки ISession.Сессия NHibernate закрывается, хотя зарегистрированный тип использует Unity за запрос

Я получаю ошибку как "Session is closed! Object name: 'ISession'. Может ли кто-нибудь помочь, что я делаю неправильно здесь? Ниже вы найдете мой код.

unityconfig:

container.RegisterType<IUnitOfWork, UnitOfWork>(new ContainerControlledLifetimeManager()); 

public class UnitOfWork : IUnitOfWork 
{ 
    private static readonly ISessionFactory _sessionFactory; 
    private ITransaction _transaction; 

    public ISession Session { get; set; } 

    static UnitOfWork() 
    { 
     _sessionFactory = Fluently.Configure() 
      .Database(MsSqlConfiguration.MsSql2008.ConnectionString(x => x.FromConnectionStringWithKey("UnitOfWorkExample"))) 
      .Mappings(x => x.AutoMappings.Add(
       AutoMap.AssemblyOf<Product>(new AutomappingConfiguration()).UseOverridesFromAssemblyOf<ProductOverrides>())) 
      .ExposeConfiguration(config => new SchemaUpdate(config).Execute(false, true)) 
      .BuildSessionFactory(); 
    } 

    public UnitOfWork() 
    { 
     Session = _sessionFactory.OpenSession(); 
    } 

    public void BeginTransaction() 
    { 
     _transaction = Session.BeginTransaction(); 
    } 

    public void Commit() 
    { 
     try 
     { 
      if (_transaction != null && _transaction.IsActive) 
       _transaction.Commit(); 
     } 
     catch 
     { 
      if (_transaction != null && _transaction.IsActive) 
       _transaction.Rollback(); 

      throw; 
     } 
     finally 
     { 
      Session.Dispose(); 
     } 
    } 

    public void Rollback() 
    { 
     try 
     { 
      if (_transaction != null && _transaction.IsActive) 
       _transaction.Rollback(); 
     } 
     finally 
     { 
      Session.Dispose(); 
     } 
    } 
} 

WebAPI Действие фильтра:

public class UnitOfWorkActionFilter : ActionFilterAttribute 
{ 
    public IUnitOfWork UnitOfWork { get; set; } 

    public override void OnActionExecuting(HttpActionContext actionContext) 
    { 
     UnitOfWork = actionContext.Request.GetDependencyScope().GetService(typeof(IUnitOfWork)) as IUnitOfWork; 
     UnitOfWork.BeginTransaction(); 
    } 

    public override void OnActionExecuted(HttpActionExecutedContext actionExecutedContext) 
    { 
     UnitOfWork = actionExecutedContext.Request.GetDependencyScope().GetService(typeof(IUnitOfWork)) as IUnitOfWork; 
     if (actionExecutedContext.Exception == null) 
     { 
      // commit if no exceptions 
      UnitOfWork.Commit(); 
     } 
     else 
     { 
      // rollback if exception 
      UnitOfWork.Rollback(); 
     } 
    } 
} 
+0

где вы получаете исключение? это на 'UnitOfWork.Commit();' –

+0

на линии _transaction = Session.BeginTransaction(); –

+0

, когда я делаю запрос к webapi в первый раз, когда он работает, но второй раз, когда я делаю запрос, его не вызывает конструктор. Думаю, здесь что-то делать? –

ответ

1

Использование PerRequestLifetimeManager вместо ContainerControlledLifetimeManager и посмотреть. ContainerControlledLifetimeManager регистрирует существующий объект как экземпляр singleton, который не является тем, что вы хотите.

увидеть это для получения дополнительной информации MSDN

+0

, когда я пытаюсь использовать этот контейнер. RegisterType (новый PerRequestLifetimeManager()); Я получаю тип или пространство имен, не найденное для PerRequestLifetimeManager –

+0

Является ли это TransientLifeTimeManager? –

+0

Когда я использовал TransientLifeTimeManager, он сработал. Спасибо –