Структура моего веб-приложения следующая:
У меня есть классы DAO (для каждого конкретного экземпляра), унаследованные от BaseDAO<T, TId>
. (Где T
может быть что-то вроде «Клиенты»).
Базовый класс содержит свойство HibernateTemplate
.
У меня есть базовый класс для контроллеров MVC (с унаследованными).
У меня есть базовый класс для Service (модель сервиса M + V + C +) (с унаследованными единицами для экземпляра (например, «CustomersService»)).
У меня есть базовый класс для класса DAO (с унаследованными в каждом экземпляре ...) (разделенный в другом проекте VS).
У меня есть классы объектов POCO (для каждой таблицы базы данных), отображения (и отношения между которыми) определены в XML-файле для Hibernate.
Приложение, которое в данный момент работает, управляет всеми вещами следующим образом (оно функционирует как функционирование - я получил его, как это было реализовано ранее):
Контроллеры MVC включают некоторые служебные свойства (которые необходимы для работы контроллеров) и инициализируются Spring через определения XML-файлов.
(например, UsersController
может иметь свойства UsersService
и UsersRolesServices
)
Каждый сервис включает соответствующее свойство DAO-helper (например, UsersService имеет свойство UsersDAO), инициализация которого также определена в файле xml (для Spring).
Итак, в общем случае (поскольку каждая такая инициализация определяется в файле xml) вся эта структура инициализируется Spring в начале жизненного цикла страницы. И все работает хорошо.
... кроме удобства процесса разработки
... поскольку мне нужно заранее определить "все везде", т. е. скажем, на случай, если мне понадобится также UsersWearService
в UsersController
, тогда я должен определить его свойство в UsersController
и перейдите в XML-файл и добавьте его инициализацию. Так что это так неудобно и негибко.
Что я пытался сделать:
Я создал метод GetService<UsersService>().GetAllUsers()
(только пример)
который создает сервис динамически через Activator.CreateInstance
(он позволяет вызывать любой сервис на любом контроллере без какого-либо предварительного определения). Все было хорошо, за исключением того, что у меня не было HibernateTemplate (== null) (так как он не был "активирован" через Spring). Поэтому я попытался получить этот объект через Application.Current.Context
и GetObject
, чтобы получить шаблон HibernateTemplate через Spring + Hibernate.
Все даже начало работать, но только с простыми запросами.
Если я попытаюсь сделать что-то вроде этого:
GetService<UsersService>()
.GetAllUsers()
.Where(x => x.UsersEmailsAmount.Count > 0)
(при ленивой загрузке дочерних коллекций)
... он получает следующее исключение:
«Не удалось лениво инициализировать коллекцию - ни один сеанс или сеанс не был закрыт».
После всего этого я даже попытался добавить какое-то свойство в Controller / Service / Dao (к базовому классу) (которое должно было бы определять только Controller в файле XML-файла гибернации), и я даже получил свойство HibernateTemplate, хорошо инициализированное, но в этой ленивой операции загрузки у меня все то же исключение.
Кажется, в случае такой динамической загрузки "что-то", "где-то" все еще не инициализирована ссылка на сессию (даже если я получаю объект HibernateTemplate через Spring), но я не знаю, где это "что-то" и "где-то" , Я чувствую, что все это происходит вокруг объектов POCO с некоторым внутренним поведением Hibernate, но я не могу видеть, как все эти вещи связаны друг с другом.
Может кто-нибудь дать мне хоть какую-нибудь подсказку, что с этим не так, или даже если теоретически возможно реализовать то, что я хотел? (Я верю, что все, что можно сделать в разработке, но вопрос, стоит ли это того времени).
Я новичок в hibernate, и ребята, которые разрабатывали это приложение, готовы тратить столько времени на все эти определения, но это так неудобно и не так очевидно (даже не говоря о новых разработчиках (особенно без какой-либо документации!) )