NHibernate, et impair "Session is Closed!" Erreurs

Note: Maintenant que j'ai tapé, je dois m'excuser pour le super longue question, cependant, je pense que tout le code et les informations présentées ici est, d'une certaine façon pertinente.


D'accord, je suis bizarre "de la fermeture de la Session" les erreurs, à des points aléatoires dans mon ASP.NET formulaires de demande. Aujourd'hui, cependant, c'est enfin passe au même endroit, encore et encore. Je suis près certain que rien n'est de l'élimination ou de la fermeture de la session dans mon code, comme les morceaux de code qui utilisent sont bien contenues à l'écart de tous les autres code comme vous le verrez ci-dessous.

Je suis également en utilisant ninject que mon CIO, qui peuvent /ne peuvent pas être important.

Bon, alors, tout d'Abord, ma SessionFactoryProvider et SessionProvider classes:


SessionFactoryProvider

public class SessionFactoryProvider : IDisposable
{
    ISessionFactory sessionFactory;

    public ISessionFactory GetSessionFactory()
    {
        if (sessionFactory == null)
            sessionFactory =
                Fluently.Configure()
                        .Database(
                            MsSqlConfiguration.MsSql2005.ConnectionString(p =>
                                p.FromConnectionStringWithKey("QoiSqlConnection")))
                        .Mappings(m =>
                            m.FluentMappings.AddFromAssemblyOf<JobMapping>())
                        .BuildSessionFactory();

        return sessionFactory;
    }

    public void Dispose()
    {
        if (sessionFactory != null)
            sessionFactory.Dispose();
    }
}

SessionProvider

public class SessionProvider : IDisposable
{
    ISessionFactory sessionFactory;
    ISession session;

    public SessionProvider(SessionFactoryProvider sessionFactoryProvider)
    {
        this.sessionFactory = sessionFactoryProvider.GetSessionFactory();
    }

    public ISession GetCurrentSession()
    {
        if (session == null)
            session = sessionFactory.OpenSession();

        return session;
    }

    public void Dispose()
    {
        if (session != null)
        {
            session.Dispose();                
        }
    }
}

Ces deux classes sont câblés avec Ninject de la manière suivante:

NHibernateModule

public class NHibernateModule : StandardModule
{        
    public override void Load()
    {
        Bind<SessionFactoryProvider>().ToSelf().Using<SingletonBehavior>();
        Bind<SessionProvider>().ToSelf().Using<OnePerRequestBehavior>();
    }
}

et aussi loin que je peux dire à fonctionner comme prévu.

Maintenant mon BaseDao<T> classe:


BaseDao

public class BaseDao<T> : IDao<T> where T : EntityBase
{
    private SessionProvider sessionManager;
    protected ISession session { get { return sessionManager.GetCurrentSession(); } }

    public BaseDao(SessionProvider sessionManager)
    {
        this.sessionManager = sessionManager;
    }        

    public T GetBy(int id)
    {
        return session.Get<T>(id);
    }

    public void Save(T item)        
    {
        using (var transaction = session.BeginTransaction())
        {
            session.SaveOrUpdate(item);

            transaction.Commit();
        }
    }

    public void Delete(T item)
    {
        using (var transaction = session.BeginTransaction())
        {
            session.Delete(item);

            transaction.Commit();
        }
    }

    public IList<T> GetAll()
    {
        return session.CreateCriteria<T>().List<T>();
    }

    public IQueryable<T> Query()
    {
        return session.Linq<T>();
    }        
}

Qui est lié à Ninject comme suit:


DaoModule

public class DaoModule : StandardModule
{
    public override void Load()
    {
        Bind(typeof(IDao<>)).To(typeof(BaseDao<>))
                            .Using<OnePerRequestBehavior>();
    }
}

Maintenant le web demande qui est à l'origine de ce est quand je suis à la sauvegarde d'un objet, il n'a pas eu lieu jusqu'à j'ai apporté quelques modifications au modèle d'aujourd'hui, cependant, les changements à mon modèle n'a pas changé le code d'accès aux données dans de toute façon. Si elle a changé un peu de mappages NHibernate (je peux poster ces trop si quelqu'un est intéressé)

D'aussi loin que je peux dire, BaseDao<SomeClass>.Get est appelé ensuite BaseDao<SomeOtherClass>.Get est appelé ensuite BaseDao<TypeImTryingToSave>.Save est appelé.

c'est le troisième appel à la ligne dans Save()

using (var transaction = session.BeginTransaction())

qui échoue avec "la Session est Fermée!" ou plutôt de l'exception:

Session is closed!
Object name: 'ISession'.

Description: An unhandled exception occurred during the execution of the current web request. Please review the stack trace for more information about the error and where it originated in the code. 

Exception Details: System.ObjectDisposedException: Session is closed!
Object name: 'ISession'.

Et en effet, suite à la Débogueur affiche le troisième temps de la séance est demandée à partir du SessionProvider il est en effet fermé et n'est pas connecté.

J'ai vérifié que Dispose sur mon SessionFactoryProvider et sur mon SessionProvider sont appelés à la fin de la demande, et pas avant la Save appel est effectué sur mon Dao.

Alors maintenant, je suis un peu coincé. Un peu de choses de la pop à l'esprit.

  • Suis-je en train de faire quelque chose de toute évidence mal?
  • Ne NHibernate jamais fermer les sessions sans me demander?
  • Des solutions de contournement ou des idées sur ce que je pourrais faire?

Merci d'avance

source d'informationauteur Sekhat