【问题标题】:h:dataTable always displays one row; won't display zero rowsh:dataTable 总是显示一行;不会显示零行
【发布时间】:2019-07-14 09:47:00
【问题描述】:

我正在使用旧版 JSF Web 应用程序,而我的 h:dataTable 元素给我带来了麻烦。通常,它会准确地显示我想要的方式 - 一个标题和几行,所有这些都具有适当的填充和边距以及所有内容。

但是,如果我尝试显示一个零行的表格(这对我来说是一个有效的用例),JSF 仍会呈现一行,尽管内容为空。

这是这个 h:dataTable 的源代码:

<h:dataTable styleClass="table" value="#{backingBean.emptyList}" var="result">

    <h:column>
        <f:facet name="header">First Column</f:facet>
        <h:outputText value="#{result}"/>
    </h:column>

    <h:column>
        <f:facet name="header">Second Column</f:facet>
        <h:outputText value="#{result}"/>
    </h:column>

    <h:column>
        <f:facet name="header">Third Column</f:facet>
        <h:outputText value="#{result}"/>
    </h:column>

</h:dataTable>

这是浏览器正在呈现的内容:

<table class="table">
    <thead>
        <tr>
            <th scope="col">First Column</th>
            <th scope="col">Second Column</th>
            <th scope="col">Third Column</th>
        </tr>
    </thead>
    <tbody>
        <tr>
            <td></td>
            <td></td>
            <td></td>
        </tr>
    </tbody>
</table>

以下是支持 bean 中的方法,它们为我提供了我的结果列表:

public List<String> getEmptyList() { // incorrectly renders 1 empty row
    return Collections.emptyList();
}

public List<String> getThreeRows() { // correctly renders 3 rows
    return Arrays.asList(new String[] {"row1", "row2", "row3"});
}

为什么 JSF 渲染这个空行?我原以为&lt;tbody&gt; 只是空的。这是 JSF 的正确行为吗?还是我配置错误?

请指教,

-八月

【问题讨论】:

  • 因为您的结果集包含一个为空的条目??? minimal reproducible example
  • 我已将问题更新为更简洁。
  • 似乎可以重现:即使是一个微不足道的数据表 &lt;h:dataTable&gt;&lt;h:column/&gt;&lt;/h:dataTable&gt; 也有一个带有一行的主体:&lt;table&gt; &lt;tbody&gt; &lt;tr&gt;&lt;td&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt; &lt;/table&gt;
  • 这就是 JSF2 的工作原理吗?我很惊讶它正在渲染 。也许这是一个有意识的设计决定?或者可能是一个错误?
  • 我无法想象这是一个错误,除非您使用的是最新最好的快照并且这是一个遗漏。

标签: css jsf jsf-2


【解决方案1】:

根据 Mojarra 2.3.8 的源代码,这是一种鼓励行为,TableRenderer(正如它的名字所说)负责和explicitly doing this

com.sun.faces.renderkit.html_basic.TableRenderer.encodeChildren(FacesContext, UIComponent):

if(!renderedRow) {
        // if no row with data has been rendered, render that empty row in question:
        this.renderEmptyTableRow(writer, data);
}

您的选择包括:

1) 给你的dataTable添加一个渲染属性:

<h:dataTable value="#{backingBean.entityList}"
  rendered="#{not empty backingBean.entityList}" ...>
  ...
</h:dataTable>
<h:outputText rendered="#{empty backingBean.entityList}"
  value="No data to display, sooo sorry :-("/>

2) 覆盖 TableRenderer 以更好地满足您的需求:

package my;

import java.io.IOException;

import javax.faces.component.UIComponent;
import javax.faces.component.UIData;
import javax.faces.context.FacesContext;

import com.sun.faces.renderkit.html_basic.TableRenderer;

public class CustomTableRenderer extends TableRenderer {
    @Override
    public void encodeChildren(final FacesContext context, final UIComponent component) throws IOException {
        final UIData data = (UIData) component;
        final int rowCount = data.getRowCount();
        if (rowCount > 0) {
            super.encodeChildren(context, component);
        } else {
            // do what super.encodeChildren does, but your way ...
        }
    }
}

遗憾的是,您不能只覆盖 com.sun.faces.renderkit.html_basic.TableRenderer.renderEmptyTableRow(ResponseWriter, UIComponent) 并让它什么都不做,因为它是 private

faces-config.xml注册你的自定义渲染器:

<render-kit>
    <renderer>
        <component-family>javax.faces.Data</component-family>
        <renderer-type>javax.faces.Table</renderer-type>
        <renderer-class>my.CustomTableRenderer</renderer-class>
    </renderer>
</render-kit>

编辑:有问题的行为是在 in a commit 修复 issue #1009 with comment 时引入的:

Fix for issue 1009: Rendered h:dataTable/h:panelGrid without rows/content do not validate against XHTML 1.0 Transitional (and html4)

git-svn-id: https://svn.java.net/svn/mojarra~svn/trunk@7669 761efcf2-d34d-6b61-9145-99dcacc3edf1

太糟糕了,我再也找不到那个问题了,but @Kukeltje did!

【讨论】:

  • 嘿,谢谢!只要 Sun 有目的地决定渲染一个空行,我想我就不会改变它。我只是害怕我搞砸了我的xhtml。感谢您的澄清。
  • @AugustZellmer 不客气。我刚刚编辑了答案,在提交中添加了一个链接,确认这是故意行为。
  • 看看为什么 JSF 版本信息总是与帖子相关!
  • 问题现在在 github 中,如果您在旧 java.net 站点的原始问题编号上添加 4,您会再次遇到问题:github.com/javaserverfaces/mojarra/issues/1013
  • @Kukeltje nice1 不知道-thanx :-)
猜你喜欢
相关资源
最近更新 更多
热门标签