2015-04-14 29 views
1

这个问题是从前一个问题的后续“禁用时为true的InputText值null”,但我无法给它添加注释。jsf inputText禁用和只读属性的形式

我使用jsf 2.2和设置为true时的禁用和只读属性,对于包含在窗体中的inputText和inputTextarea控件,由于字段合并对象时数据库中的关联字段正在删除数据从jsf页面返回对象时为空。

在窗体的字段上设置这些属性的目的是在字段中显示数据,但不允许用户更改它并将更改保存到窗体中的其他字段。

除了将字段放置在表单之外并使页面布局复杂化之外,还可以实现其他什么方法。

格雷厄姆

+0

请问您可以发布一些代码。因为我无法重现此行为所有预期的工作,与残疾人和只读后提交值保持正常。 – pL4Gu33

回答

1

我解决了这个问题,它是通过使用@RequestScoped而不是@SessionScoped我的页面控制器豆引起的。

我在做什么是使用编辑链接从数据表中传递当前产品对象到doEditProduct方法。

   <h:dataTable id="viewProductsTable" value="#{productController.products}" var="_product" 
         styleClass="data-table" headerClass="table-header" rowClasses="table-row"> 
       <h:column> 
        <f:facet name ="header"> 
         <h:outputText value="Product Name" /> 
        </f:facet> 
        <h:outputText value="#{_product.productName}"/> 
       </h:column> 
       <h:column> 
        <f:facet name="header"> 
         <h:outputText value="Goal"/> 
        </f:facet> 
        <h:outputText value="#{_product.goal}"/> 
       </h:column> 
       <h:column> 
        <f:facet name="header"> 
         <h:outputText value="Details"/> 
        </f:facet> 
        <h:outputText value="#{_product.description}"/> 
       </h:column> 
       <h:column> 
        <h:form> 
         <h:commandLink value="Edit" action="#{productController.doEditProduct(_product)}"/> 

        </h:form> 
       </h:column> 
      </h:dataTable> 

的productController.doEditProduct方法然后打开编辑页面

public String doEditProduct(Product product) { 
    this.product = product; 
    return "edit-product.xhtml"; 

编辑页面包含一个简单的编辑形式

   <h:form id="addProductForm"> 
       <h:panelGrid columns="2" columnClasses="top-alignment, top-alignment"> 
        <h:outputLabel for="product-name" value="Product Name"/> 
        <h:outputText value="#{productController.product.productName}" id="product-name" /> 
        <h:outputLabel for="goal" value="Goal" /> 
        <h:inputTextarea value="#{productController.product.goal}" id="goal" rows="10" cols="100" /> 
        <h:outputLabel for="details" value="Details" /> 
        <h:inputTextarea value="#{productController.product.description}" id="details" rows="20" cols="100"/> 
        <f:facet name="footer"> 
         <h:panelGroup style="padding-top: 15px; display: inline-block; float: right; white-space: nowrap"> 
          <h:commandButton id="submit" value="Save" action="#{productController.updateProduct()}" class="button" /> 
          <h:button id="Cancel" outcome="index.xhtml" value="Cancel" class="button"/> 
         </h:panelGroup> 
        </f:facet> 

       </h:panelGrid> 
      </h:form> 

此时产品数据显示在页面上。然而,当点击保存按钮并运行更新方法时

public String updateProduct() { 
    try { 
     log.log(Level.INFO, "Updating: {0}", product.getGoal()); 
     productFacade.edit(product); 
    } catch (Exception e) { 
     log.log(Level.WARNING, e.toString()); 
     String errorMessage = getRootErrorMessage(e); 
     FacesMessage m = new FacesMessage(FacesMessage.SEVERITY_ERROR, errorMessage, "could not update product"); 
     facesContext.addMessage(null, m); 
     return ""; 

    } 
    return "index.xhtml"; 

任何已被禁用或只读的字段被设置为空。实际上,页面上任何位置的任何非输入字段都设置为空。

控制器类上的@RequestScope意味着类正在被重新实例化,因此存储在产品中的对象被分配了PostConstruct方法中的新对象。可编辑字段中的值被转移到这个新对象,并且不可编辑字段被设置为空。与数据库合并意味着字段中的数据被删除。

使用@SessionScoped意味着控制器bean跨页请求继续存在。 (我需要提醒自己的基本网页生命周期)

希望这可以帮助任何其他人有这种行为。

格雷厄姆