我正在努力解决一个问题,我试图使用JSF 2.1和Primefaces为一种CMS项目动态生成页面。我的问题是我试图使用自定义ResourceResolver动态地包含一个存在于数据库中的页面(该部分工作得很好)。问题是我使用请求参数来确定要服务的页面(即:http://xxx.xxx.com/context/public/?p=2)。这工作正常,直到我想使用任何Ajax或更具体的Primefaces(在我的情况下,我需要使用actionListeners的计划组件)。我发现在发出ajax请求时我的视图没有得到解决,可能是因为它是请求作用域。下面是一些代码:
<?xml version='1.0' encoding='UTF-8' ?>
<!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:h="http://java.sun.com/jsf/html"
xmlns:p="http://primefaces.org/ui"
xmlns:ui="http://java.sun.com/jsf/facelets">
<ui:composition template="/WEB-INF/view/public/templates/public-template.xhtml">
<ui:define name="body">
<p:outputPanel autoUpdate="false" rendered="#{empty publicBean.site}">
<div>No site found!</div>
</p:outputPanel>
<p:outputPanel autoUpdate="false" rendered="#{! empty publicBean.page and empty publicBean.page.pageTemplate}">
<div>No valid page template found!</div>
</p:outputPanel>
<ui:include src="#{publicBean.view}" />
</ui:define>
</ui:composition>
</html>
视图的数量是未知的并且是动态创建的,因此,我不能只做一个丑陋的ui块:包含并有条件地渲染。
所以我所看到的是,当我这样做时,我的基于ajax的表单(例如使用p:commandButton)不起作用。我从来没有看到我的豆子上执行的动作。但是如果我硬编码从“#{publicBean.view}”返回的视图,那么它总是返回相同的视图,一切正常。所以我假设在ajax调用期间,publicBean.view可能返回null或者在我的情况下返回AgoraConstants.CUSTOM_VIEW_NOT_FOUND。这是我的支持bean中的代码:
public String getView()
{
// If this below is uncommented, the form with ajax/primefaces works
//if ( 1 == 1 )
//{
// return "/X-AGORA-VIEW/districtOfficeCalendarTemplate.xhtml";
//}
if ( page != null && page.getPageTemplate() != null )
{
return AgoraConstants.CUSTOM_VIEW_PREFIX + page.getPageTemplate().getName() + ".xhtml";
}
else if ( site != null && site.getLandingPage() != null && site.getLandingPage().getPageTemplate() != null )
{
return AgoraConstants.CUSTOM_VIEW_PREFIX + site.getLandingPage().getPageTemplate().getName()+".xhtml";
}
return AgoraConstants.CUSTOM_VIEW_NOT_FOUND;
}
所以这是我的问题,我如何保持请求参数,以便我可以使用ajax和primefaces以我想要的方式工作?我可以在会话中抛出它,但是如果用户在具有不同视图的两个选项卡中打开网站,事情可能会混淆并且无法正常运行。基本上,我应该如何保持请求变量,以便我可以确保getView()为ajax请求返回相同的视图?似乎应该有一个简单的解决方案,但我没有看到任何帮助将不胜感激。
**编辑**
我也尝试更改我的支持bean来查看作用域(来自请求),但这似乎没有帮助(但我不知道为什么)。下面是更多的支持bean代码。我添加了init方法,当使用@PostConstruct创建bean时调用该方法。
public void init()
{
site = null;
page = null;
logger.info("Loading public view...");
if ( getFacesContext().getExternalContext().getRequestParameterMap().containsKey(AgoraConstants.PUBLIC_PAGE_REQUEST_VAR) )
{
logger.info("Restoring Page...");
long value = parseLong((String)getFacesContext().getExternalContext().getRequestParameterMap().get(AgoraConstants.PUBLIC_PAGE_REQUEST_VAR));
if ( value >= 0 )
{
logger.info("Attempting to restore: {}", value);
try
{
page = pageService.getItem(value);
if ( page != null )
{
if ( ! page.isEnabled() )
{
page = null;
}
}
}
catch(Exception e)
{
logger.warn("Failed to load site: {}", e.getLocalizedMessage());
}
}
}
if ( page == null && getFacesContext().getExternalContext().getRequestParameterMap().containsKey(AgoraConstants.PUBLIC_SITE_REQUEST_VAR) )
{
logger.info("Restoring Site...");
long value = parseLong((String)getFacesContext().getExternalContext().getRequestParameterMap().get(AgoraConstants.PUBLIC_SITE_REQUEST_VAR));
if ( value >= 0 )
{
logger.info("Attempting to restore: {}", value);
try
{
site = siteService.getItem(value);
}
catch(Exception e)
{
logger.warn("Failed to load site: {}", e.getLocalizedMessage());
}
}
}
if ( page != null && page.getSite() != null)
{
site = page.getSite();
}
if ( site == null )
{
site = siteService.getDefaultSite();
}
}
public String getView()
{
// if ( 1 == 1 )
// {
// return "/X-AGORA-VIEW/districtOfficeCalendarTemplate.xhtml";
// }
if ( page != null && page.getPageTemplate() != null )
{
logger.info("a" + AgoraConstants.CUSTOM_VIEW_PREFIX + page.getPageTemplate().getName() + ".xhtml");
return AgoraConstants.CUSTOM_VIEW_PREFIX + page.getPageTemplate().getName() + ".xhtml";
}
else if ( site != null && site.getLandingPage() != null && site.getLandingPage().getPageTemplate() != null )
{
logger.info("b" + AgoraConstants.CUSTOM_VIEW_PREFIX + site.getLandingPage().getPageTemplate().getName()+".xhtml");
return AgoraConstants.CUSTOM_VIEW_PREFIX + site.getLandingPage().getPageTemplate().getName()+".xhtml";
}
logger.info("c");
return AgoraConstants.CUSTOM_VIEW_NOT_FOUND;
}
答案 0 :(得分:0)
在这种情况下你应该使用视图范围bean,但是在使用视图范围和动态ui:include时会出现问题。您可以测试它,例如将断点放在构造函数中,您将看到在每个请求中创建了bean。如果您使用例如c:if或c:for。
,也会出现问题答案 1 :(得分:0)
我的整个问题是因为post-backs不包含ajax请求的请求参数,所以我正在使用prettyfaces来解决这个问题。有了漂亮的面孔,我设置了映射,以便在回发后包含请求参数,这解决了我的问题。这可能不适用于所有情况,但它似乎对我有用。