我对JSF有一个非常奇怪的问题,但是我无法自行解决它,因为我没有任何错误消息可供Google使用。问题是,我有一种观点来提交新文章或更新现有文章。某些方法不被视图调用
方法getArticle()返回 - 如果?id = x通过url设置 - 文章POJO的id为x。否则,一个纯粹的空新文章。根据ID设置,模式editArticle设置为true或false。
因此,如果我通过URL传递一个id,表单将更改为“更新文章”,并显示文章的值。但是如果我点击提交按钮,什么都不会发生。没有输出,没有错误。在Firefox中使用HTTP Live Headers,我可以看到服务器的请求。在loopback接口上使用wireshark,也有流量。
但另一方面,“创建新文章” - 巴顿(如果id没有设置)没有问题。 )(环境:JSF 2.2,Apache Tomcat 7/8,Java 7/8,Windows/Ubuntu(尝试不同的envs,但总是相同的,所以它似乎是一个“设计”问题:-))。也尝试重命名方法,通过ActionListener调用,改变panelGrids的顺序......但没办法。点击按钮决不会调用bean的updateArticle()方法。
<h:form id="idMasterForm" enctype="multipart/form-data">
<h:panelGroup rendered="#{userController.loggedIn}">
<h:panelGrid columns="2" cellpadding="5">
<p:outputLabel for="title" value="Title" />
<p:inputMask id="title"
value="#{editArticleController.article.title}" />
<p:outputLabel for="author" value="Author" />
<p:inputText id="author" value="#{userController.id}"
readonly="true" />
<p:outputLabel for="date" value="Date" />
<p:inputMask id="date"
value="#{editArticleController.article.date}" readonly="true" />
<p:outputLabel for="link" value="File" />
<p:selectOneMenu id="link"
value="#{editArticleController.article.link}">
<f:selectItems value="#{uploadFilesController.filesItems}" />
</p:selectOneMenu>
<p:outputLabel for="editor" value="" />
<p:editor id="editor" widgetVar="editorWidget"
value="#{editArticleController.article.text}" width="600" />
</h:panelGrid>
<h:panelGrid columns="2" style="margin-top: 10px" rendered="#{!editArticleController.editArticle}">
<p:commandButton value="Submit new article"
action="#{editArticleController.createArticle()}"
icon="ui-icon-disk" />
<p:commandButton value="Clear" type="button"
onclick="PF('editorWidget').clear();" icon="ui-icon-close" />
</h:panelGrid>
<h:panelGrid columns="2" style="margin-top: 10px" rendered="#{editArticleController.editArticle}" >
<p:commandButton value="Update article"
action="#{editArticleController.updateArticle()}"
icon="ui-icon-disk" />
<p:commandButton value="Clear" type="button"
onclick="PF('editorWidget').clear();" icon="ui-icon-close" />
</h:panelGrid>
<h:outputText rendered="#{ ! userController.loggedIn}"
value="#{res.globNotLoggedIn}" />
</h:panelGroup>
</h:form>
这里是Managed Bean的:
import java.util.Date;
import javax.faces.bean.ManagedBean;
import javax.faces.context.FacesContext;
import javax.servlet.http.HttpServletRequest;
import hwr.Util;
import hwr.g2.model.Archive;
import hwr.g2.model.Article;
import hwr.g2.model.Author;
import hwr.user.UserController;
@ManagedBean
public class EditArticleController {
private Article article;
private Boolean editArticle;
private Integer editArticleID;
public EditArticleController() {
this.article = new Article();
System.out.println("EditArticleController was called");
}
public Article getArticle() {
//System.out.println("getArticle() was called");
if (this.getEditArticle()) {
this.article = new Article(this.editArticleID);
}
return this.article;
}
public void setArticle(Integer articleID) {
this.article = new Article(articleID);
}
public void setArticle(Article article) {
System.out.println("setArticle(Article article) was called");
this.article = article;
}
public void setText(String text) {
this.article.setText(text);
}
public String getText() {
return this.article.getText();
}
public void setTitle(String title) {
this.article.setTitle(title);
}
public String getTitle() {
return this.article.getTitle();
}
public Boolean getEditArticle() {
// https://stackoverflow.com/questions/550448/get-request-and-session-parameters-and-attributes-from-jsf-pages
HttpServletRequest req = (HttpServletRequest) FacesContext
.getCurrentInstance().getExternalContext().getRequest();
try {
this.editArticleID = Integer.valueOf(req.getParameter("id"));
if (this.editArticleID > 0) {
this.setEditArticle(true);
} else {
this.setEditArticle(false);
}
} catch (Exception e) {
this.setEditArticle(false);
}
return editArticle;
}
public void setEditArticle(Boolean editArticle) {
this.editArticle = editArticle;
}
public Date getActualDate() {
Date d = new Date();
return d;
}
public void rangChanged() {
// nothing
}
public String createArticle() {
System.out.println("New Article...");
Util util = new Util();
UserController user = (UserController) util.getBean("userController");
this.article.setAuthor(new Author(user.getId()));
this.article.setDate(new Date());
try {
Archive archive = new Archive();
archive.addArticle(this.article);
} catch (Exception e) {
System.out.println("something goes wrong here...");
e.printStackTrace();
}
return "g2_home?faces-redirect=true";
}
public String updateArticle() {
System.out.println("*** Update Article... ***");
System.out.println("Debug: Update article, ID "
+ this.article.getId() + "! title: " + this.article.getTitle()
+ " and text: " + this.article.getText()
+ " and written by "
+ this.article.getAuthor().getFirst());
try {
Archive archive = new Archive();
archive.updateArticle(this.article);
} catch (Exception e) {
System.out.println("something goes wrong here...");
e.printStackTrace();
}
return "g2_home?faces-redirect=true";
}
}
我用BalusC(action method is not called in JSF)的清单,但没有发现什么。 如果有人能指引我正确的方向,它应该是非常棒的。顺便说一句,有没有更好的方式来填写表格?以我的方式,getArticle()方法被视图多次调用。
Kudos @BalusC!我删除了两个按钮,并通过“保存文章”按钮替换它们而没有“渲染”。被调用的函数根据editArticle的状态调用createArticle()或updateArticle()。 所以得出的结论是:从来没有把一个动作按钮放在一个表单中并保持getter非常简单? – xentity