gpt4 book ai didi

jsf-2 - PrimeFaces selectCheckboxMenu : Old values in toggleSelect actionListener

转载 作者:行者123 更新时间:2023-12-04 12:56:28 26 4
gpt4 key购买 nike

在我的 JSF View 中,我有一个 p:selectCheckboxMenu我想通过 AJAX 对选定的值执行一些业务逻辑。

对于一个简单的 change事件它工作正常,但对于 toggleSelect事件不是。在我的监听器方法中,我正在检索旧的选择,但我期待这里的新选择。

请参阅以下示例:

@ViewScoped
@Named
public class RequestBean implements Serializable {
private List<String> list; // + getter/setter

@PostConstruct
private void init() {
list = new ArrayList<String>() {{
add("one"); add("two"); add("three");
}};
}

public void listener() {
System.out.println("Current content of \"list\":");
for(String s : list) {
System.out.println(s);
}
}
}

在 JSF View 中:
<p:selectCheckboxMenu value="#{requestBean.list}" label="List">
<f:selectItem itemValue="one" itemLabel="one"/>
<f:selectItem itemValue="two" itemLabel="two"/>
<f:selectItem itemValue="three" itemLabel="three"/>
<p:ajax event="toggleSelect" listener="#{requestBean.listener}" />
<p:ajax event="change" listener="#{requestBean.listener}" />
</p:selectCheckboxMenu>

现在让我们考虑以下用例:您正在进入 View ,选择了“一”和“二”。如果我单击“全选”复选框,结果是:
Info:   Current content of "list":
Info: one
Info: two

但预期的结果是这样的:
Info:   Current content of "list":
Info: one
Info: two
Info: three

对于常规更改事件,它按预期工作。在这里,我在监听器中获得了新的选择。我该如何解决?或者我做错了什么?

GlassFish 4.1, running on Java 1.8.0_45

JSF 2.2.10 (Mojarra)

PrimeFaces 5.1

OmniFaces 1.8.1

最佳答案

这个问题似乎与过早调用监听器有关。做一些基本的调试,我发现 toggleSelect在更新模型值之前调用监听器方法,而 change事件在修改它们后执行。这是我目前的代码:

请求 bean :

@ViewScoped
@ManagedBean
public class RequestBean implements Serializable {
public List<String> getList() {
return list;
}

public void setList(List<String> list) {
this.list = list;
System.out.println("Values set: " + list);
}

private List<String> list;

@PostConstruct
private void init() {
list = new ArrayList<String>() {
{
add("one");
add("two");
add("three");
}
};
}

public void listener() {
System.out.println("Listener called!");
}
}

page.xhtml:
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://xmlns.jcp.org/jsf/html"
xmlns:f="http://xmlns.jcp.org/jsf/core"
xmlns:p="http://primefaces.org/ui"
xmlns:comp="http://java.sun.com/jsf/composite/comp"
xmlns:ui="http://java.sun.com/jsf/facelets">
<h:head />
<h:body>
<h:form>
<p:selectCheckboxMenu value="#{requestBean.list}" label="List">
<f:selectItem itemValue="one" itemLabel="one" />
<f:selectItem itemValue="two" itemLabel="two" />
<f:selectItem itemValue="three" itemLabel="three" />
<p:ajax event="toggleSelect" listener="#{requestBean.listener}" />
<p:ajax event="change" listener="#{requestBean.listener}" />
</p:selectCheckboxMenu>
</h:form>
</h:body>
</html>

这就是您当前步骤的跟踪:
Values set: [one]
Listener called!
Values set: [one, two]
Listener called!
Listener called!
Values set: [one, two, three]

最后一个是工具选择,您可以看到模型已正确更新,但之前调用了监听器。

让我们多玩一点自定义 PhaseListener :
Entering RESTORE_VIEW 1
Entering APPLY_REQUEST_VALUES 2
Entering PROCESS_VALIDATIONS 3
Entering UPDATE_MODEL_VALUES 4
Values set: [one]
Entering INVOKE_APPLICATION 5
Listener called!
Entering RENDER_RESPONSE 6
Entering RESTORE_VIEW 1
Entering APPLY_REQUEST_VALUES 2
Entering PROCESS_VALIDATIONS 3
Entering UPDATE_MODEL_VALUES 4
Values set: [one, two]
Entering INVOKE_APPLICATION 5
Listener called!
Entering RENDER_RESPONSE 6
Entering RESTORE_VIEW 1
Entering APPLY_REQUEST_VALUES 2
Listener called!
Entering PROCESS_VALIDATIONS 3
Entering UPDATE_MODEL_VALUES 4
Values set: [one, two, three]
Entering INVOKE_APPLICATION 5
Entering RENDER_RESPONSE 6

如您所见,模型值始终设置在 UPDATE_MODEL_VALUES 中。相,而 change事件在 INVOKE_APPLICATION 执行理所当然, toggleSelect听众表演在 APPLY_REQUEST_VALUES ,在列表之前。

这似乎是一个 Primefaces 错误,应该在 their GitHub branch 中通知.

另见:
  • How to implement a PhaseListener which runs at end of lifecycle?
  • 关于jsf-2 - PrimeFaces selectCheckboxMenu : Old values in toggleSelect actionListener,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29746618/

    26 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com