Validation 使用回发覆盖JSF viewParam,然后重定向到其自身
我有一个JSF2.0页面,我想允许GET参数进入该页面,并设置bean的值。此外,我希望允许从同一页面上的表单修改该bean,然后使用新的GET参数重定向回同一页面。正如您可能期望的那样,我希望这样可以将页面添加到书签中 但是,当原始GET请求包含重新验证的bean的无效(验证失败)参数时,我遇到了问题。这个问题一开始对我来说并不明显,但在检查日志后,它变得非常明显。当commandButton检查新键入的值的有效性时,JSF将验证原始GET参数以及新键入的值。由于GET参数首先未能通过验证,因此再次失败。不幸的是,这阻止了新值的出现 即使GET值有效,也会在验证新值之前再次检查它们,这是浪费时间。无论GET参数是否通过验证,是否有一种方法可以在加载GET参数后基本上丢弃这些参数,从而只验证当前值 详情: 我在主页上包含了一个搜索表单,它进行Ajax验证(使用Validation 使用回发覆盖JSF viewParam,然后重定向到其自身,validation,jsf-2,primefaces,facelets,Validation,Jsf 2,Primefaces,Facelets,我有一个JSF2.0页面,我想允许GET参数进入该页面,并设置bean的值。此外,我希望允许从同一页面上的表单修改该bean,然后使用新的GET参数重定向回同一页面。正如您可能期望的那样,我希望这样可以将页面添加到书签中 但是,当原始GET请求包含重新验证的bean的无效(验证失败)参数时,我遇到了问题。这个问题一开始对我来说并不明显,但在检查日志后,它变得非常明显。当commandButton检查新键入的值的有效性时,JSF将验证原始GET参数以及新键入的值。由于GET参数首先未能通过验证,因
h:inputText
和p:commandButton
(Primefaces)进行标准bean验证),但在我使用h:commandButton
时也会失败),以确保用户提交数据(不是空白)。验证成功后,使用以下操作重定向页面:
listing?faces-redirect=true&includeViewParams=true
表格:
<h:form id="search">
<p:messages id="qError" />
<h:inputText value="#{pageSearchBean.search}" id="q"
validator="#{pageSearchBean.validateSearchNotBlank}" />
<p:commandButton value="Find" action="#{pageSearchBean.searchAction}"
update="qError" />
</h:form>
现在,在列表页面上,我通过导入相同的Facelet重用了完全相同的搜索表单/Facelet,但我也显示了实际搜索的结果,这与您使用过的几乎所有搜索页面类似
按原样,页面总是进行双重检查
public class PageSearchBean implements Serializable
{
protected static final Log LOGGER =
LogFactory.getLog(PageSearchBean.class);
protected final List<Page> results = new ArrayList<Page>();
protected String search = "";
public String getSearch()
{
// all logging just to watch how things are requested
LOGGER.fatal(String.format("getSearch() = '%s'", search));
return search;
}
public void setSearch(String search)
{
LOGGER.fatal(String.format("setSearch('%s')", search));
this.search = search;
}
public List<Page> getResults()
{
return results;
}
public void doSearch()
{
LOGGER.fatal(String.format("doSearch() for '%s'", getSearch()));
// generate random data/search results (if we haven't already
// and we have search terms)
}
public String searchAction()
{
LOGGER.fatal("searchAction()");
return "listing?faces-redirect=true&includeViewParams=true";
}
public void validateSearchNotBlank(FacesContext context,
UIComponent validate,
Object value)
throws ValidatorException
{
LOGGER.fatal(String.format("validate('%s')", value));
// throws new ValidatorException when blank (null or all whitespace)
}
}
公共类PageSearchBean实现可序列化
{
受保护的静态最终日志记录器=
getLog(PageSearchBean.class);
受保护的最终列表结果=新建ArrayList();
受保护字符串搜索=”;
公共字符串getSearch()
{
//所有日志记录只是为了观察请求的内容
LOGGER.fatal(String.format(“getSearch()=“%s”,搜索));
返回搜索;
}
公共无效集合搜索(字符串搜索)
{
LOGGER.fatal(String.format(“setSearch('%s')”,search));
this.search=搜索;
}
公共列表getResults()
{
返回结果;
}
公共无效数据搜索()
{
LOGGER.fatal(String.format(“用于“%s”的doSearch(),getSearch());
//生成随机数据/搜索结果(如果我们还没有
//我们有搜索词)
}
公共字符串searchAction()
{
LOGGER.fatal(“searchAction()”);
返回“listing?faces redirect=true&;includeViewParams=true”;
}
public void validateSearchNotBlank(FacesContext上下文,
组件验证,
对象值)
抛出验证器异常
{
LOGGER.fatal(String.format(“validate('%s')”,value));
//为空时引发新的ValidatorException(null或所有空白)
}
}
一个没有吸引力的解决方案是避免在JSF级别验证GET参数,而只是在setter级别验证值(忽略其中的无效数据)
因为我愿意为我的用例接受未设置的参数,所以这是一个不错的解决方法。然而,我希望有一个更有用的解决方案,使我能够避免将setter与验证混为一谈,因为JSF页面无法避免双重验证
public class PageSearchBean implements Serializable
{
protected static final Log LOGGER =
LogFactory.getLog(PageSearchBean.class);
protected final List<Page> results = new ArrayList<Page>();
protected String search = "";
public String getSearch()
{
// all logging just to watch how things are requested
LOGGER.fatal(String.format("getSearch() = '%s'", search));
return search;
}
public void setSearch(String search)
{
LOGGER.fatal(String.format("setSearch('%s')", search));
this.search = search;
}
public List<Page> getResults()
{
return results;
}
public void doSearch()
{
LOGGER.fatal(String.format("doSearch() for '%s'", getSearch()));
// generate random data/search results (if we haven't already
// and we have search terms)
}
public String searchAction()
{
LOGGER.fatal("searchAction()");
return "listing?faces-redirect=true&includeViewParams=true";
}
public void validateSearchNotBlank(FacesContext context,
UIComponent validate,
Object value)
throws ValidatorException
{
LOGGER.fatal(String.format("validate('%s')", value));
// throws new ValidatorException when blank (null or all whitespace)
}
}