Jsf 2 获取数据库条目的正确代码模式是什么?

Jsf 2 获取数据库条目的正确代码模式是什么?,jsf-2,Jsf 2,在另外两个问题(和)中,BalusC做出了一个直截了当的声明: getter只是用来访问bean属性,而不是做一些业务逻辑。这里有bean构造函数、初始化块或事件方法。在bean的生命周期中,所有这些都只执行一次,这正是您想要的 哎呀,这让我已经写了无数行代码无效了。那么,实现填充数据表的支持bean的正确方法是什么?我理解他的观点和理念,但不理解他的实践。我的问题有两个: 为什么我这样做是错误的 我怎么修理它 我经常使用PrimeFacesp:dataTable,它的值属性解析为一个集合。出于

在另外两个问题(和)中,BalusC做出了一个直截了当的声明:

getter只是用来访问bean属性,而不是做一些业务逻辑。这里有bean构造函数、初始化块或事件方法。在bean的生命周期中,所有这些都只执行一次,这正是您想要的

哎呀,这让我已经写了无数行代码无效了。那么,实现填充数据表的支持bean的正确方法是什么?我理解他的观点和理念,但不理解他的实践。我的问题有两个:

  • 为什么我这样做是错误的
  • 我怎么修理它
  • 我经常使用PrimeFacesp:dataTable,它的属性解析为一个集合。出于我不在这里讨论的原因,我不使用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">
    
    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;
    }
    
    
    
    现在,dataModel的异常糟糕的UN JSFish(或者我刚刚发现的)getter如下所示:

     <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">
    
    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;
    }
    
    公共ATMDataModel getDataModel(){ TableQueryParameters p=getTableQueryParameters(); 如果(p.isChangePending())clearDataModel(); p、 setChangePending(假); 如果(dataModel!=null)返回dataModel; List List=getDAO().runQuery(p); if(p.isNeedResultSize())p.setResultSize(getDAO().runQueryCount(p)); 数据模型=新的ATMDataModel(列表); 返回数据模型; } 一些解释

  • 这来自一个抽象的超类,其中ET是“实体类型”。我所有的CRUD都使用相同的例程
  • ATMDataModel是实现SelectableListModel的列表的包装器。PrimeFaces中的行选择逻辑需要这样做。(这是PF 3中出现的一种痛苦,但它使行选择工作更加可靠。)
  • TableQueryParameters是我编写的用来封装用户屏幕上表的当前状态的东西。它包括什么样的排序参数、什么样的筛选参数、我们所处的页面等等。因为这需要保留,所以支持bean是ViewAccesScoped(通过MyFaces CODI),而TableQueryParameters是其中的一个属性
  • TableQueryParameters通过AJAX事件进行响应更新,AJAX事件也会更新表单,从而调用getDataModel。当任何更改时,方法isChangePending将变为true。因此,getDataModel方法使用它在更改之间只从DAO生成一次获取,而不管调用了多少次
  • 但是如果TableQueryParameters确实发生了变化,我必须使用这些参数调用runQuery,以获取用户想要查看的新记录集。如果我不在getDataModel中调用它,我在哪里调用它


    请告知。

    您基本上是在惰性地将数据加载到getter中。在同一请求(或视图)范围内的每个getter调用中,您都没有命中DB。这是负担得起的。我不使用CODI,但我可以想象,
    getTableQueryParameters()
    调用也特别便宜,不需要担心

    至于具体的问题,您通常会使用附加到
    UICommand
    组件和/或ajax事件标记的action(listener)方法来执行DB/business任务

    例如(但也可以用作


    根据
    p.isChangePending()
    的含义,我认为您也可以通过这种方式消除它,看起来您是在action(listener)方法中设置它。

    您基本上是在getter中惰性地加载数据。在同一请求(或视图)范围内的每个getter调用中,您都没有命中DB。这是负担得起的。我不使用CODI,但我可以想象,
    getTableQueryParameters()
    调用也特别便宜,不需要担心

    至于具体的问题,您通常会使用附加到
    UICommand
    组件和/或ajax事件标记的action(listener)方法来执行DB/business任务

    例如(但也可以用作


    根据
    p.isChangePending()
    的含义,我认为您也可以通过这种方式消除它,看起来您是在action(listener)方法中设置的。

    好的,所以我想我的答案是我没有做错。我已经在各种不同的框架中编写CRUD例程将近30年了,所以这次远离基础会让人震惊!这里使用CODI的唯一原因是,我可以同时使用CDI和ViewScope功能。此处设置ViewScope的唯一原因是保存TableQueryParameters。谢谢你的意见。好吧,我想我的答案是我没有做错。我已经在各种不同的框架中编写CRUD例程将近30年了,所以这次远离基础会让人震惊!这里使用CODI的唯一原因是,我可以同时使用CDI和ViewScope功能。此处设置ViewScope的唯一原因是保存TableQueryParameters。谢谢你的意见。