Вот копия сообщения, которое я сделал в группе NHUsers ( Ссылка на обсуждение, в котором также обсуждаются несколько других подходов )
Я знаю, что у вас есть консольное приложение, имое приложение - WinForms, но тот же подход должен работать и для вас.Это не идеально, но пока что работает на меня.
=====================================================
Управление сессиями при использовании NHibernate, отложенной загрузки и WinForms кажется тем, с чем многие люди борются - язнайте, что я сделал!
Добавление привязки данных WinForms к миксу является дополнительным усложнением в моем проекте, который имеет единственную основную форму, сосредоточенную вокруг стороннего элемента управления сеткой.Сетка привязана к моей объектной модели через интерфейс IBindingList.
После долгой борьбы и растягивания волос подход, который , похоже, работает , состоит в том, чтобы создать MainSession дляОсновная форма, которая остается открытой большую часть времени.Это означает, что всякий раз, когда пользователи перемещаются по данным с помощью сетки, существует открытый сеанс для обработки ленивых загрузок данных из базы данных.
Для других операций (обновления, удаления и т. Д.) Я отключаю основноесеанс, создайте новый одноразовый сеанс только для этой операции, а затем снова подключите основной сеанс.
Это работает, и если это поможет кому-то еще, отлично.Тем не менее, я не полностью доверяю этому, и кажется, что каждый раз, когда я добавляю новую возможность (удаление было самой последней), она ломается и должна быть снова настроена.Если у кого-нибудь есть лучшее предложение, я бы с удовольствием его услышал.
И наоборот, если все в порядке, я бы тоже хотел это знать - теперь я буду спать лучше.
В любом случае, вот некоторый код, взятый из моего проекта для иллюстрации подхода.
/// <summary>
/// NHibernate session factory used by the application
/// </summary>
private static ISessionFactory _sessionFactory;
/// <summary>
/// NHibernate session used by MainForm. Kept open most of the time to facilitate
/// lazy loading of data. Disconnected and Reconnected when app writes
/// new data to database
/// </summary>
private static ISession _mainSession;
/// <summary>
/// Get the main database session, creating it if necessary
/// </summary>
/// <returns></returns>
private static ISession GetMainSession()
{
if (_sessionFactory == null)
{
CreateSqliteSessionFactory();
}
if (_mainSession == null)
{
_mainSession = _sessionFactory.OpenSession();
}
return _mainSession;
}
private static void DisconnectMainSession()
{
GetMainSession().Disconnect();
}
private static void ReconnectMainSession()
{
GetMainSession().Reconnect();
}
/// <summary>
/// Save measurement to DB. Does not check for duplicates
/// </summary>
/// <param name="measurement"></param>
public static void SaveMeasurement(object measurement)
{
DisconnectMainSession();
using (var session = _sessionFactory.OpenSession())
using (var transaction = session.BeginTransaction())
{
try
{
session.Save(measurement);
transaction.Commit();
session.Close();
}
catch (Exception e)
{
if (transaction != null) transaction.Rollback();
throw new ApplicationException(
"\r\n SaveMeasurement exception:\r\n\r\n", e);
}
finally
{
ReconnectMainSession();
}
}
}