EL-条件运算符 ?: 在复合组件中的意外行为

EL-Conditional operator ?: in composite component unexpected behavior

野飞8、JSF 2.2

如果复合组件中的条件运算符 ? :c:foreach 循环中的列表一起使用,则其行为不正确。

示例文件的输出是

eng germ ital

并不像预期的那样

eng eng germ germ ital ital

如果复合组件重写为ui:includetaglib那么预期的结果就来了

文件(test.xhtml):

<html xmlns="http://www.w3.org/1999/xhtml" xmlns:h="http://java.sun.com/jsf/html" xmlns:f="http://java.sun.com/jsf/core"
    xmlns:ui="http://java.sun.com/jsf/facelets" 
    xmlns:fn="http://java.sun.com/jsp/jstl/functions" xmlns:my="http://java.sun.com/jsf/composite/myComp"
    xmlns:c="http://java.sun.com/jsp/jstl/core">

<h:body>
   <my:testConditionalOperator languagesList="#{['eng', 'germ', 'ital']}"></my:testConditionalOperator>
</h:body>
</html>

复合组件(testConditionalOperator.xhtml):

<!DOCTYPE html>
<html lang="en" xmlns="http://www.w3.org/1999/xhtml" xmlns:a="http://xmlns.jcp.org/jsf/passthrough"
    xmlns:of="http://omnifaces.org/functions" xmlns:f="http://xmlns.jcp.org/jsf/core"
    xmlns:c="http://java.sun.com/jsp/jstl/core" xmlns:o="http://omnifaces.org/ui" xmlns:h="http://xmlns.jcp.org/jsf/html"
    xmlns:ui="http://xmlns.jcp.org/jsf/facelets" xmlns:fn="http://xmlns.jcp.org/jsp/jstl/functions"
    xmlns:cc="http://java.sun.com/jsf/composite">
    <cc:interface>
        <cc:attribute name="languagesList"></cc:attribute>
    </cc:interface>
    <cc:implementation>
        <c:forEach var="language" items="#{cc.attrs.languagesList}" >
            #{fn:length(cc.attrs.languagesList) gt 1 ?  language : "a"}
            <c:if test="#{fn:length(cc.attrs.languagesList) gt 1}">
                #{language}
            </c:if>
        </c:forEach>
    </cc:implementation>
</html>

这似乎是一个没有出现在 MyFaces 中的 Mojarra 错误。

解决方法是,在 end 属性中设置大小并使用 varStatus 获取它。

<cc:implementation>
    <c:forEach var="language" items="#{cc.attrs.languagesList}" end="#{cc.attrs.languagesList.size()}" varStatus="loop">
        #{loop.end gt 1 ?  language : "a"}
        <c:if test="#{loop.end gt 1}">
            #{language}
        </c:if>
    </c:forEach>
</cc:implementation>

注意 EL 2.2 仅使用 size() 而不是 fn:length()

的能力