在使用<c:if>
有条件地使用复合组件时,我收到重复的ID异常
我知道这个编译/渲染时间问题,但我真的不知道为什么下面的例子不起作用。
请看一下以下三个简单的片段
名为 TestBean 的会话范围bean,它包含一个布尔值,以及两个将此值更改为true或false的ajax侦听器:
@Named
@SessionScoped
public class TestBean implements Serializable {
private boolean isVisible = false;
public void onSetItemVisible(AjaxBehaviorEvent e) {
this.isVisible = true;
}
public void onSetItemInvisible(AjaxBehaviorEvent e) {
this.isVisible = false;
}
public boolean isItemVisible() {
return this.isVisible;
}
}
一个名为 testCmp 的非常简单的复合组件:
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:cc="http://java.sun.com/jsf/composite">
<cc:interface/>
<cc:implementation>
<h:outputText id="text" value="text"/>
</cc:implementation>
</html>
一个允许在隐藏/显示此复合组件
之间切换的视图页面<h:body>
<h:form id="testForm">
<c:if test="#{testBean.itemVisible}">
<test:testCmp id="test1"/>
</c:if>
<p/>
<test:testCmp id="test2"/>
<p/>
<!-- show/hide dynamic item -->
<h:commandLink value="Show Item">
<f:ajax execute="@this" listener="#{testBean.onSetItemVisible}" render="@form"/>
</h:commandLink>
<br/>
<h:commandLink value="Hide Item">
<f:ajax execute="@this" listener="#{testBean.onSetItemInvisible}" render="@form"/>
</h:commandLink>
</h:form>
</h:body>
事情是:当我在show / hide之间切换时,我得到一个重复的ID异常。 异常说:“组件ID testForm:test2:文本已在视图中找到”
它抱怨'test2'......没有条件添加的组件。
当我不使用复合组件并将其替换为<h:outputText>
之类的标准组件时,任何方法都可以正常工作。
要重现错误,重要的是,复合组件在同一页面上使用两次,一次使用,而其他时间没有条件。
经过进一步搜索,我发现另一个我认为和我一样有问题的家伙。但他的例子看起来有点复杂,难以重现。 Duplicate component ID in JSF using composite component twice in view
任何人都有线索在这里发生什么? 我的设置是JBoss EAP7和Mojarra JSF 2.2.14(但我也测试了JSF 2.3.0-m11) 有人可以确认这个问题吗? 如果是这样,我会为mojarray家伙制造一个错误。
答案 0 :(得分:2)
这绝对是Mojarra中的一个错误,与在某些情况下处理动态组件树修改有关。
我创建了一个复制品,提交了一个问题,并将我的发现写到了mojarra dev邮件列表中。请在https://github.com/tuner/mojarra-dynamic-include-reproducer
了解详情答案 1 :(得分:1)
在data = objects.map(item => { return item.speed; })
labels = objects.map(item => { return formatAMPM(item.fixTime); })
内使用<c:if>
时遇到了同样的问题。
绕过我发现的这个错误的唯一方法是使用<cc:implementation>
而不是<h:panelGroup rendered="#{condition}">
。