【问题标题】:JSF - f:ajax execute does not update the backing property of beanJSF - f:ajax 执行不更新 bean 的支持属性
【发布时间】:2013-01-17 01:31:48
【问题描述】:

我有两个组件,一个 commandButton 和一个 selectOneListbox。

单击命令按钮后,我需要更新绑定到 selectOneListBox 的支持属性的值。

两个组件都在同一个<h:form> 中。 支持 Bean 是 Named/SessionScoped bean。

这是我页面中定义组件的部分:

按钮:

    <h:commandButton formnovalidate="formnovalidate" title="Select Variable" 
                     type="button" styleClass="button_green close_window" 
                     tabindex="2" id="btnSelectVar" value="Confirm">
         <f:ajax execute="lstVarSelected" event="click" 
                 listener="#{systemOptionsControl.updateText}" onevent="updateParent"/>
    </h:commandButton>


SelectOneListBox: (selectedVariable is a String and variables is a List of String)


    <h:selectOneListbox id="lstVarSelected" name="lstVarSelected" 
                        tabindex="1" value="#{systemOptionsControl.selectedVariable}" >
        <f:selectItems value="#{systemOptionsControl.variables}"/>
    </h:selectOneListbox>

单击按钮后,我需要获取 oneListBox 的支持属性,但 JSF 没有在支持 bean 上调用 set 方法。然后,当我尝试获取 updateText 方法的值时,我得到了 NullPointerException。

我尝试了很多解决方案,但都没有奏效,任何人都可以提供任何想法吗?

这里是 xhtml:

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd" >
<html xmlns="http://www.w3.org/1999/xhtml"
      xmlns:ui="http://java.sun.com/jsf/facelets"
      xmlns:h="http://java.sun.com/jsf/html"
      xmlns:escriba="http://java.sun.com/jsf/composite/components/escriba"
      xmlns:f="http://java.sun.com/jsf/core" lang="pt-br" class="no-js">
    <body>
        <h:head>
            <h:outputScript name="jsf.js" library="javax.faces"/>
            <script language="javascript">
                function callParentButton(data) {
                    //Verifica o status da execução do ajax. 
                    var status = data.status;
                    //alert(status);
                    switch(status)
                    {
                        case 'begin':
                            break; 
                        case 'complete':
                            //Gets the name of parent button
                            var a = #{systemOptionsControl.idBtnAtualizarTextAreas}; 
                            //Calls the click.
                            var btn = document.getElementById(a.valueOf().name);
                            btn.click();
                            break;
                        } 
                    }
            </script>
        </h:head>
        <h:form prependId="false" id="frmVariables">
            <section class="box_padrao">
                <header id="box_padrao_header">
                    <h1>System Options</h1>            
                    <div id="actions_menu">
                        <h:commandButton type="button" title="Select Variable" styleClass="button_green" tabindex="2" 
                                         id="btnConfirmar" value="Confirm">
                            <f:ajax execute="lstVariables" event="click" listener="systemOptionsControl.updateText" onevent="callParentButton"/>
                        </h:commandButton>
                        <button type="button" title="Cancel" class="button_red close_window" tabindex="3" id="btnCancelar" name="btnCancel">Cancel</button>
                    </div> 
                </header>
                <div class="box_padrao_content">
                    <div class="grid_100">
                        <h2 class="legend">» Variables List </h2>   
                        <fieldset class="fieldset">
                            <div class="grid_100">
                                <h:selectOneListbox id="lstVariables" name="lstVariables" tabindex="1" value="#{systemOptionsControl.selectedVariable}" >
                                    <f:selectItems value="#{systemOptionsControl.variables}"/>
                                </h:selectOneListbox>
                            </div>
                        </fieldset>
                    </div>      
                </div>
            </section>
        </h:form> 
    </body>
</html>

这是 Bean:

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package br.com.xxx.rodrigoms.control;


import java.util.ArrayList;
import java.util.List;
import javax.annotation.PostConstruct;
import javax.enterprise.context.SessionScoped;
import javax.inject.Named;

/**
 *
 * @author rodrigos
 */
@Named
@SessionScoped
public class SystemOptionsControl{    

    private String selectedVariable;

    @PostConstruct
    public void initialize() {
        //non-matter code
    }

    //<editor-fold desc="GETS/SETS">
    public String getIdBtnAtualizarTextAreas(){
        return "btnUpdateTextAreas";
    }

    public String getSelectedVariable() {
        return selectedVariable;
    }

    public void setSelectedVariable(String selectedVariable) {
        this.selectedVariable = selectedVariable;
    }

    public List<String> getVariables() {
        List<String> ret = new ArrayList<>();
        //just simulating
        ret.add("1");
        ret.add("2");
        ret.add("3");
        ret.add("4");
        return ret;
    }

    //</editor-fold>

    //<editor-fold desc="Other methods">
    public void updateText(){
        //I get the NullPointerException right on next line
        String variavelAInserir = "<".concat(this.selectedVariable).concat(">");,

        /*
        code do other suffs
        */
    }
    //</editor-fold>

    }

很抱歉有任何语言错误,需要更改一些名称,因为它是公司的“工作”。

【问题讨论】:

  • 监听方法你在做什么?为什么你的 commandButton 类型是按钮? formnovalidate 到底在做什么?
  • 按钮和列表框是否放在同一个&lt;h:form&gt;中?其余的,请仔细阅读stackoverflow.com/questions/2118656/…中提到的要点
  • formnovalidate 是我试图让它发挥作用的一种尝试 :( @BalusC:是的。我之前读过这篇文章,但没有发现任何与此相关的问题。如果你愿意,我可以提供完整的网页.
  • 只要复制粘贴到一个完全空白的模板就足够了,它只是适合&lt;h:body&gt; 的最小可能的 sn-p 并为我们(和您!)重现问题。我们将假设一个完全空的&lt;h:head&gt;。尽可能小的 bean 示例,包括必要的导入,也会有所帮助。
  • 好的,我会试试的,我在这个问题上卡了几个小时。请稍候。

标签: java ajax jsf execute


【解决方案1】:

嗯,我用绑定属性解决了。

在我的 bean 中绑定了一个 inputTextArea 之后。我能够在侦听器方法中获取 selectedValue。

执行未“真正”执行 set 方法的原因是在我尚未发现的侦听器执行之前。

无论如何,谢谢你们两个人的大力帮助 :) 这是我第一次在 stackoverflow 中提问,你们两个非常有说服力:)

谢谢!

【讨论】:

    【解决方案2】:

    您没有提供足够的关于您的支持 bean 或 xhtml 页面的信息。 甚至你提供的部分也包含太多无效的语法,所以我决定做一个例子。

    这是给你的。

    SystemOptionsControl.java

    import java.util.Arrays;
    import java.util.List;
    import javax.faces.bean.ManagedBean;
    import javax.faces.bean.ViewScoped;
    import javax.faces.model.SelectItem;
    
    
    @ManagedBean
    @ViewScoped
    public class SystemOptionsControl {
    
        private Integer selectedVariable;
        private List<SelectItem> variables = Arrays.asList(new SelectItem(1),
                                                           new SelectItem(2),
                                                           new SelectItem(3));
    
        public void updateText(){
            System.out.print("updateText method invoked");
            System.out.print("Selected Value " + selectedVariable);        
        }
    
        public Integer getSelectedVariable() {
            return selectedVariable;
        }
    
        public void setSelectedVariable(Integer selectedVariable) {
            this.selectedVariable = selectedVariable;
        }
    
        public List<SelectItem> getVariables() {
            return variables;
        }
    
        public void setVariables(List<SelectItem> variables) {
            this.variables = variables;
        }
    }
    

    Page.xhtml

    <html xmlns="http://www.w3.org/1999/xhtml"
          xmlns:h="http://java.sun.com/jsf/html"
          xmlns:f="http://java.sun.com/jsf/core">
    
        <h:head>
            <title>Title</title>
        </h:head>
    
        <h:body>
    
            <h:form prependId="false">
    
                <h:commandButton type="button" id="btnSelectVar" value="Confirm">
                    <f:ajax execute="lstVarSelected" event="click" listener="#{systemOptionsControl.updateText}" />
                </h:commandButton>
    
    
                <h:selectOneListbox id="lstVarSelected" value="#{systemOptionsControl.selectedVariable}" >
                    <f:selectItems value="#{systemOptionsControl.variables}"/>
                </h:selectOneListbox>
    
            </h:form>
    
        </h:body>
    
    </html>
    

    【讨论】:

    • 这段代码和我的一样。我们的“代码”之间的唯一区别是我使用 List 而不是 SelectItem 的列表。我现在会尝试改变这一点。
    • 即使使用 SelectItems 列表,也不会调用“selSelectedVariable”。 :(
    • 上面的代码可以正常工作。用它。一步步修改,直到坏掉。发布破坏您的代码的内容。
    猜你喜欢
    • 2011-06-26
    • 2013-05-07
    • 2017-04-12
    相关资源
    最近更新 更多