我有这个页面,我有两个表格。第二种形式由ajax加载(呈现)。问题是,当按下下一个表单的按钮时,页面只是重新加载,而不是实际调用'action'中指定的方法。
XHTML
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE composition PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<ui:composition xmlns:ui="http://java.sun.com/jsf/facelets"
template="./../WEB-INF/employeeTemplate.xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core"
xmlns="http://www.w3.org/1999/xhtml">
<ui:define name="content">
finding user ...
<h:form id="mainForm">
<h:inputText id="userId" value="#{eFindUser.userId}" />
<h:commandButton value="Render!" action="#{eFindUser.findUser}" >
<f:ajax event="action" execute="userId" render="@all" />
</h:commandButton>
</h:form>
<h:panelGroup id="result">
<h:panelGroup layout="block" rendered="#{eFindUser.notFound}" style="color:red">
User not found
</h:panelGroup>
<h:form>
<h:panelGroup layout="block" rendered="#{eFindUser.responseRendered}" >
<h:inputHidden value="#{eFindUser.user}" />
<table>
<tr>
<td>Name</td> <td>#{eFindUser.user.name}</td>
</tr>
<tr>
<td>Balance:</td> <td>#{eFindUser.user.account.balance}</td>
</tr>
<tr>
<td><h:commandButton value="update balance" action="#{eFindUser.process()}" /></td>
</tr>
</table>
</h:panelGroup>
</h:form>
</h:panelGroup>
</ui:define>
</ui:composition>
支持bean
/*
* To change this template, choose Tools | Templates
* and open the template in the editor.
*/
package backingbeans;
import entities.User;
import java.io.Serializable;
import java.util.Random;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ViewScoped;
import javax.inject.Inject;
import javax.validation.constraints.NotNull;
import stateless.EmployeeFacade;
/**
*
* @author Martin
*/
@ManagedBean(name="eFindUser")
@ViewScoped
public class EFindUserManagedBean implements Serializable{
private static final long serialVersionUID = -7106162864352727534L;
private boolean responseRendered = false;
private boolean notFound = false;
@NotNull
private Long userId;
private User user;
@Inject
private EUpdateBalanceManagedBean updateBalance;
@Inject
private EmployeeFacade employeeFacade;
/**
* Creates a new instance of EFindUserManagedBean
*/
public EFindUserManagedBean() {
}
public void findUser() {
if(new Random().nextDouble() < 0.3) {
notFound = true;
responseRendered = false;
} else {
notFound = false;
responseRendered = true;
user = employeeFacade.getUserById(3L);
}
}
public boolean isResponseRendered() {
return responseRendered;
}
public void setResponseRendered(boolean responseRendered) {
this.responseRendered = responseRendered;
}
public boolean isNotFound() {
return notFound;
}
public void setNotFound(boolean notFound) {
this.notFound = notFound;
}
public Long getUserId() {
return userId;
}
public void setUserId(Long userId) {
System.out.println("blah");
this.userId = userId;
}
public User getUser() {
return user;
}
public void setUser(User user) {
System.out.println("setting user");
this.user = user;
}
public String process() {
updateBalance.setUser(user);
System.out.println("process");
return "/employee/updateBalance.xhtml?faces-redirect=true";
}
}
当我点击第一个'渲染!' - 标记按钮时,它就像魅力一样。第二个表单已加载并准备工作。当我点击下一个“更新余额”标记的按钮时,页面只是重新加载它当然不应该。它应该重定向到“/ employee / updateBalance”。或者至少应该调用流程方法。
非常感谢
编辑:@BalusC是对的,答案在上一个问题中答案 0 :(得分:0)
罪魁祸首可以在第二种形式的<h:inputHidden>
标签中找到:
<h:form>
<h:panelGroup layout="block" rendered="#{eFindUser.responseRendered}" >
<h:inputHidden value="#{eFindUser.user}" />
</h:panelGroup>
</h:form>
最有可能是它的绑定值,eFindUser.user
的类型为User
,当您提交该表单时,JSF不知道如何使用User
对象分配用户的字符串表示形式。
因此,存在转换错误,根据JSF生命周期,在这种情况下不调用action方法。此外,如果您的视图中有<h:messages>
,您就会知道。
可以做的是:
<h:inputHidden value="#{eFindUser.user}" converter="userConverter"/>
,并已实施@FacesConverter
。可以找到更多详细信息here。<h:inputHidden>
绑定到String
,以便不需要转换器:<h:inputHidden value="#{eFindUser.user.userNickname}">
或Integer
以类似的方式。答案 1 :(得分:0)
修改
<h:commandButton value="update balance" action="#{eFindUser.process()}" />
至
<h:commandButton value="update balance" action="#{eFindUser.process}" />
el表达式不能包含“()”