Управление сеансом NHibernate в ASP.NET MVC

В настоящее время я играю с классом HybridSessionBuilder, найденным в сообщении блога Джеффри Палермо:

http://jeffreypalermo.com/blog/use-this-nhibernate-wrapper-to-keep-your-repository-classes-simple/

Используя этот класс, мой репозиторий выглядит так:

public class UserRepository : IUserRepository
{
    private readonly ISessionBuilder _sessionBuilder;

    public UserRepository(ISessionBuilder sessionBuilder)
    {
        _sessionBuilder = sessionBuilder;
    }

    public User GetByID(string userID)
    {
        using (ISession session = _sessionBuilder.GetSession())
        {
            return session.Get<User>(userID);
        }
    }
}

Это лучший способ управления сеансом / фабрикой NHibernate? Я слышал кое-что о Unit of Work и создании сеанса для каждого веб-запроса и его сбросе в конце. Насколько я могу судить, моя текущая реализация ничего из этого не делает. Он в основном полагается на репозиторий, чтобы получить сеанс из фабрики сеансов и использовать его для выполнения запросов.

Есть ли подводные камни при таком доступе к базе данных?


person Kevin Pang    schedule 13.12.2008    source источник
comment
не уверен в подводных камнях, но вы можете проверить реализацию шаблона Unit of Work с использованием Rhino.Commons на сайте Стива Болена www.autumnofagile.net ... он создает приложение MVC с NHibernate, Windsor и Rhino.Common ... это отличная серия   -  person Webjedi    schedule 13.12.2008


Ответы (5)


Вы не должны заключать ISession в оператор using - точка передачи ISessionBuilder в конструктор репозитория (внедрение зависимостей) заключается в том, что вызывающий код отвечает за управление жизненным циклом ISession. Обернув его в using, Dispose () вызывается в ISession, и вы не сможете лениво загружать элементы объекта или сохранять его.

Мы делаем нечто подобное, просто передавая ISession конструктору репозитория. Код господина Палермо, насколько я понимаю, просто добавляет ленивую инициализацию ISession. Я не думаю, что это необходимо, потому что зачем вам создавать новый репозиторий, если вы не собираетесь его использовать?

person Jamie Ide    schedule 16.12.2008

С помощью ASP.Net MVC вы хотите убедиться, что продолжительность сеанса сохраняется во время действия метода на вашем контроллере, так как после выхода вашего контроллера все ваши данные должны быть собраны. Не уверен, поможет ли этот механизм в этом.

Возможно, вы захотите изучить S # arp Architechure, который представляет собой набор библиотек и руководство по созданию приложения ASP.Net MVC с использованием nHibernate. http://code.google.com/p/sharp-architecture/

person JoshBerke    schedule 13.12.2008
comment
В настоящее время мы управляем этой сессией, используя вызовы start request и end request в global.asax (игнорируя css, js и т. Д.). Не хотели украшать каждое действие инструкцией Unit Of Work. - person Perhentian; 17.09.2009
comment
Сначала я использовал конечный запрос, но затем, когда возникла критическая ошибка, запрос уже завершился, страница была отрисована, и я не видел чистого способа обработать ошибку, кроме отправки пользователя на общую страницу. Я предпочитаю явное закрытие сеанса (или как минимум совершение транзакции) при переходе от контроллера к представлению. - person JoshBerke; 17.09.2009

Это установка, которую я использовал после того, как изучил это подробнее. Кажется, отлично работает и не имеет той раздражающей привычки создавать ISession для запросов статических файлов, как в большинстве руководств:

http://www.kevinwilliampang.com/2010/04/06/setting-up-asp-net-mvc-with-fluent-nhibernate-and-structuremap/

person Kevin Pang    schedule 07.04.2010
comment
В чем именно причина того, что он открывает сеанс для запросов статических файлов? - person Arnis Lapsa; 10.09.2010
comment
В большинстве решений используется обработчик запросов, который, поскольку IIS 7 обрабатывает все в интегрированном конвейере, обрабатывает запросы к статическим ресурсам, а не только запросы страниц. Следовательно, обработчик запускает транзакцию / сеанс Nhibernate для каждого запроса, включая запросы к статическим ресурсам. - person Ted; 30.11.2011

Я бы не стал открывать и закрывать сеансы при каждом запросе данных в NHibernate. Я бы использовал библиотеки Unit of Work, которые предлагают или читают многие другие. NHForge.org только начинается, и я считаю, что есть некоторые методы настройки NHibernate для общего веб-приложения.

Один из моментов, которые я получил от NHibernate, - это «ленивая загрузка коллекций во время разработки». Это было отличным опытом - избавиться от всех этих объединений для отображения данных о каком-то связанном объекте.

Если закрыть сеанс таким образом, описанный выше сценарий будет невозможен.

Может быть, что-то происходит и с транзакциями.

person Min    schedule 13.12.2008

Только что нашел чистое решение, использующее Unity для внедрения сеанса за запрос:

http://letsfollowtheyellowbrickroad.blogspot.com/2010/05/nhibernate-sessions-in-aspnet-mvc.html.

person Giorgio Bozio    schedule 16.05.2010