В двух других вопросах ( здесь и здесь ) BalusC делает прямое заявление:
Геттеры находятся исключительно там, чтобы получить доступ свойств бина, чтобы не заниматься бизнес-логикой.Там у вас есть конструктор компонента, блоки инициализации или методы события.Все выполняются только один раз за время жизни бина, и это именно то, что вы хотите.
Ну и дела - это просто лишило законной силы миллионный ряд кода, который я уже написал.Хорошо, тогда каков правильный способ реализации бина, который заполняет таблицу данных?Я понимаю его точку зрения и концепцию, но не практику.У меня двоякий вопрос:
- Почему я делаю это неправильно?
- Как мне это исправить?
Я использую PrimeFaces p: dataTable много, а его атрибут value разрешается в коллекцию.По причинам, которые я здесь не обсуждаю, я , а не использую функцию отложенной загрузки таблиц PrimeFaces.Вместо этого я реализую свои собственные элементы управления фильтром / сортировкой, но они запускают события AJAX, в результате чего таблица заполняется записями, извлеченными из базы данных.
Таблица размечена так:
<p:panel id="mqTable">
<h:outputText value="Sort/Filter: #{maintCategory.tableQueryParameters}" />
<p:dataTable
id="mqDataTable"
rows="#{maintCategory.pageSize}"
value="#{maintCategory.dataModel}"
selection="#{maintCategory.selected}"
var="cat"
selectionMode="single"
emptyMessage="No Categories Found">
Теперь НЕВЕРОЯТНО ПЛОХОЙ UN-JSFish (или так я только что узнал) геттер для dataModel выглядит так:
public ATMDataModel getDataModel() {
TableQueryParameters p = getTableQueryParameters();
if (p.isChangePending()) clearDataModel();
p.setChangePending(false);
if (dataModel != null) return dataModel;
List<ET> list = getDAO().runQuery(p);
if (p.isNeedResultSize()) p.setResultSize(getDAO().runQueryCount(p));
dataModel = new ATMDataModel(list);
return dataModel;
}
Несколько объяснений.
- Это из абстрактного суперкласса, где ET - это «Тип сущности».Все мои CRUDы используют эту же процедуру.
- Класс ATMDataModel - это оболочка для списка, которая реализует SelectableListModel .Логика выбора строк в PrimeFaces требует этого.(Это боль, которая появилась в PF 3, но она делает выбор строк более надежным.)
- Класс TableQueryParameters - это то, что я написал, чтобы инкапсулировать текущее состояние таблицы пользователяэкран.Он включает параметры сортировки, параметры фильтра, страницу, на которой мы находимся и т. Д. Поскольку это необходимо сохранить, базовый компонент имеет вид ViewAccesScoped (через MyFaces CODI) и TableQueryParameters это свойство внутри него.
- TableQueryParameters обновляются в ответ через события AJAX, которые также обновляют форму, вызывая getDataModel .Метод isChangePending переходит true , когда что-то меняется.Таким образом, метод getDataModel использует его для генерации только одной выборки из DAO между изменениями, независимо от того, сколько раз он вызывается.
НО , если TableQueryParameters do изменить, мне нужно вызвать runQuery с этими параметрами, чтобы получить новый набор записей, которые пользователь хочет видеть.Если я не позвоню в getDataModel , где мне это назвать?
Пожалуйста, сообщите.