vlambda博客
学习文章列表

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Chapter 3. Developing JSF 2.x Facelets

JavaServer Faces (JSF) 2.x 引入了几个新特性,例如集成Facelets、隐式导航、条件导航、抢先导航、bean验证、视图参数、客户端行为、新范围(视图、flash 和自定义)、配置注释、复合组件、资源处理程序 API、对 Ajax 的支持以及新的事件处理和异常处理功能。

WildFly 8.x 支持 JSF 2.2,即 JSF 的最新版本。 JSF 2.2 引入了方便的 HTML5 标记、资源库契约、人脸流和无状态视图的新特性。 JSF 2.2 支持已添加到具有 Maven 依赖项的项目中。在本章中,我们将在 Eclipse 中开发 JSF 2.x Facelets 应用程序,使用 Maven 构建和打包应用程序,并将应用程序部署到 WildFly 8.1。我们将在 WildFly 8.1 中运行该应用程序,以演示 Facelets 在 Web 应用程序中的使用。 Facelets 是默认的 查看JSF 2.x 中的声明语言 (VDL),将JSP 替换为默认VDL。本章包含以下部分:

  • 设置环境

  • 创建 Java EE Web 项目

  • 创建托管 bean

  • 创建 Facelets 模板

  • 创建页眉和页脚

  • 创建输入和输出 Facelets 页面

  • 创建 Web 描述符

  • 使用 Maven 安装 Web 项目

  • 运行 Facelets 应用程序

Setting up the environment


我们需要 安装以下软件:

  • WildFly 8.1.0.Final:下载 wildfly-8.1.0.Final.zip 来自 http://wildfly.org /下载/

  • MySQL 5.6 Database-Community Edition:从这个版本="ulink" href="http://dev.mysql.com/downloads/mysql/" target="_blank">http://dev.mysql.com/downloads/mysql/。安装 MySQL 时,还要安装 Connector/J

  • 面向 Java EE 开发人员的 Eclipse IDE:从 Eclipse Luna ="ulink" href="https://www.eclipse.org/downloads/packages/release/Luna/SR1" target="_blank">https://www.eclipse.org/downloads/packages/release/Luna /SR1

  • JBoss Tools (Luna) 4.2.0.Final:安装 这个为来自 Eclipse Marketplace 的 Eclipse 插件 (http://tools.jboss.org /downloads/installation.html)

  • Apache Maven:从 3.05 或更高版本ulink" href="http://maven.apache.org/download.cgi" target="_blank">http://maven.apache.org/download.cgi

  • Java 7:从 Java 7 href="http://www.oracle.com/technetwork/java/javase/downloads/index.html?ssSourceSiteId=ocomcn" target="_blank">http://www.oracle.com/technetwork/java/javase /downloads/index.html?ssSourceSiteId=ocomcn

设置环境变量JAVA_HOMEJBOSS_HOMEMAVEN_HOMEMYSQL_HOME。添加 %JAVA_HOME%/bin, %MAVEN_HOME%/bin, %JBOSS_HOME%/bin %MYSQL_HOME%/binPATH 环境变量。

创建一个 WildFly 8.1.0 运行时,如 第 1 章 EJB 3.x 入门。使用以下 SQL 脚本创建 MySQL 数据库 CATALOG

CREATE TABLE CATALOG(CatalogId INTEGER
PRIMARY KEY, Journal VARCHAR(25), Publisher VARCHAR(25), Edition VARCHAR(25), Title Varchar(45), Author Varchar(25));
INSERT INTO CATALOG VALUES('1', 'Oracle Magazine', 'Oracle Publishing', 'Nov-Dec 2004', 'Database Resource Manager', 'Kimberly Floss');
INSERT INTO CATALOG VALUES('2', 'Oracle Magazine', 'Oracle Publishing', 'Nov-Dec 2004', 'From ADF UIX to JSF', 'Jonas Jacobi');
INSERT INTO CATALOG VALUES('3', 'Oracle Magazine', 'Oracle Publishing', 'March-April 2005', 'Starting with Oracle ADF ', 'Steve Muench');

在 MySQL 5.6 命令行客户端中运行脚本。数据库表 Catalog 被创建。上述脚本的输出显示在以下屏幕截图中:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

我们还需要为 MySQL 数据库配置一个数据源。 第 1 章中讨论了配置 MySQL 数据源的过程/a>,EJB 3.x入门,本章不再赘述。

Creating a Java EE web project


在本节中,我们 将为 JSF 2.x 创建一个 Eclipse 项目。选择文件 | | Eclipse 中的其他。选择 JBoss Central | Java EE Web Project并点击Next,如图以下屏幕截图:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Java EE Web 项目 向导启动。尽管向导指示将创建 Java EE 6 Web 应用程序 项目,但仍会创建 Java EE 7 Web 应用程序项目。

针对需求运行测试,其中包括 JBoss AS 运行时、m2em2eclipse-wtp 插件和 JBoss Tools 插件,如以下屏幕截图所示。选中 Create a blank project 复选框并选择 Target Runtime 作为 < span class="strong">WildFly 8.x 运行时。点击下一步

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

指定 项目名称 (jboss- jsf2) 和 Package (org.jboss.jsf2),然后选择复选框 使用默认工作区位置。点击下一步,如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

示例项目使用的是Maven构建工具,因此需要指定Maven模块:组 ID (org.jboss.jsf2),工件 ID (jboss-jsf2), 版本 (1.0 .0) 和 Package (org.jboss.jsf2),如如下图所示。除了 name 属性,Properties available from archetype 中列出的属性可能会被删除,因为这些申请不需要。

默认的 name 属性设置为 Java EE 6 webapp project,应修改为 < span class="strong">Java EE 7 webapp 项目。点击完成

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

一个 Java EE Web 项目 得到 创建,如 Project Explorer 在以下屏幕截图中。删除 //jboss-jsf2/src/main/resources/META-INF/persistence.xml 配置文件,因为它没有在 JSF 应用程序中使用。 Web 项目在 WEB-INF/templates 目录中包含一个 default.xhtml 文件。我们将需要一个 Facelets 模板,但不需要默认模板。

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Facelets 是 http://java.sun.com/jsf/facelets 命名空间。 Facelets 标记与 JSF Core 和 JSF HTML 标记库结合使用以开发 JSF Facelets 应用程序。 Facelets 页面的默认后缀是 .xhtml。 Facelets 应用程序由以下配置和模板文件组成:

  1. Facelets 模板页面模板可以在多个 Facelets 组合中重复使用页。

  2. Facelets 页眉和页脚页面:这些页面包含在 Facelets 模板中Facelets 应用程序的常见部分的页面。

  3. 一个配置文件:这是 faces-config.xml 文件,默认情况下包含在 Java EE Web 项目中。

  4. Facelets 组合页面或页面:这些页面在 WildFly 上运行。

  5. 托管 bean:此 用于 Facelets 组合页面。

我们将创建一个带有输入 Facelets 组合页面和输出 Facelets 组合页面的 Facelets 应用程序。输入和输出页面中包含一个通用的页眉和页脚。在输入页面中,可以在输入字段中指定 SQL 查询。 SQL 查询用于从数据库中获取数据并创建 JSF 数据表并演示模板。命令按钮将输入请求参数发送到托管 bean 的操作方法。在 action 方法中,与 MySQL 数据库建立连接,并为 SQL 查询生成结果集。 JSF 数据表从结果集中生成并显示在输出 Facelets 组合页面中。

在接下来的部分中,我们将创建 Facelets 应用程序的不同组件;首先是托管bean。

Creating a managed bean


托管 bean 是由 JSF 托管 Bean 设施。托管 bean 在 JSF 中注册并在第一次调用时被实例化。在本节中,我们将为 Facelets 组合页面创建一个 JSF 托管 bean。右键单击 faces-config.xml 选择 打开方式 | Faces Config Editor,如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Faces Config Editor 已启动。点击Add添加一个托管bean,如下截图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

New Managed Bean Wizard 中,选择 Create a new Java classJava Class Selection 并点击 Next,如< id="id152" class="indexterm"> 如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Java 类 向导开始。 源文件夹jboss-jsf2/src/main/java),org.jboss.jsf2.model)和应指定名称 (Catalog),如以下屏幕截图所示。点击下一步

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Managed Bean Configuration 窗口中, Name 文本框被指定为 catalog,并且 Scope< /span> 作为 session。点击Next,如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

要创建的托管 bean 的摘要显示在 向导摘要 窗口。点击Finish,如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

创建了一个新的托管 bean catalog,如以下屏幕截图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

在托管 bean 中,导入 所需的类并使用 Catalog 类文字">@ManagedBean 注释。为输入表单(HtmlForm 类型)声明 Java bean 属性,输入文本字段(HtmlInputText 类型),输入文本字段的标签(HtmlOutputLabel 类型)、命令按钮(HtmlCommandButton 类型)、数据表(HtmlDataTable 类型)、数据表的列(UIColumn 类型)和错误消息 ( HtmlOutputText)。按照 Java bean 约定的要求,为属性添加 getter/setter 方法。此外,为 Connection 对象、Statement 对象和 ResultSet 对象。

添加一个action方法——一个没有参数并且返回一个String值和commandButton1_action的方法。在 action 方法中,使用 JDBC API 或使用 MySQL 数据源创建与 MySQL 数据库的连接。如果使用JDBC API,获取Connection对象如下:

Class.forName("com.mysql.jdbc.Driver");
String url = "jdbc:mysql://localhost:3306/test";
Connection connection = DriverManager.getConnection(url, "root", "mysql");

如果使用MySQL数据源,Connection对象获取方式如下:

InitialContext initialContext = new InitialContext();
DataSource ds = (DataSource) initialContext.lookup("java:jboss/datasources/MySQLDS");
java.sql.Connection conn = ds.getConnection();

使用 Connection 对象创建 Statement 对象createStatement 方法。使用executeQuery方法在输入字段中运行SQL查询输入,得到一个ResultSet

Statement stmt = connection.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
ResultSet rs = stmt.executeQuery((String) inputText1.getValue());

创建一个 HtmlDataTable 对象,使用 setBorder 方法设置其边框,使用 setCellpadding 方法,并使用 setVar 方法为数据集合设置迭代变量:

HtmlDataTable dataTable1 = new HtmlDataTable();
dataTable1.setBorder(5);
dataTable1.setCellpadding("1");
dataTable1.setVar("journalcatalog");

创建一个 ResultSetDataModel 对象,该对象封装了一个由 ResultSet 表示的数据集合。使用 将 SQL 查询生成的 ResultSet 设置为 ResultSetDataModel 对象的数据集合setWrappedData 方法:

ResultSetDataModel dataModel = new ResultSetDataModel();
dataModel.setWrappedData(rs);

使用 UIColumn 类构造函数为数据表创建列,并使用 setColumn 方法在数据表上设置列code class="literal">HtmlDataTablee 对象。使用 HtmlOutputText 类型变量为每列创建数据表列标题,并使用 setHeader 在列上设置标题UIColumn 对象的方法。数据表值也是 HtmlOutputText 类型。结果集数据使用值表达式绑定到数据表。 ValueExpression 对象用于设置值。 ExpressionFactory 对象是创建 ValueExpression 对象所必需的。使用 getApplication().getExpressionFactory() 从 FacesContext 对象获取 ExpressionFactory 对象代码>。首先使用 getCurrentInstance() 方法创建一个 FacesContext 对象。使用 createValueExpression(ELContext context, java.lang 从 ExpressionFactory 方法创建一个 ValueExpression 对象.String 表达式,java.lang.Class expectedType) 方法。 createValueExpression 方法的 ELContext 对象是使用 FacesContext 对象创建的getELContext() 方法。 createValueExpression 方法的表达式是 EL 表达式,expectedType 方法是 String。类。使用 setValueExpression 方法在 HtmlOutputText 类型列上设置 ValueExpression 值.使用 getChildren().add()HtmlOutputText 对象添加到 UIColumn 对象代码>。结果集值不会单独绑定到每个数据表单元格上,而是使用由迭代变量组成的 EL 表达式来绑定结果集。例如,column1,即目录 ID 的列,设置如下:

HtmlOutputText column1Text = new HtmlOutputText();
FacesContext fCtx = FacesContext.getCurrentInstance();
ELContext elCtx = fCtx.getELContext();
ExpressionFactory ef = fCtx.getApplication().getExpressionFactory();
ValueExpression ve = ef.createValueExpression(elCtx,"#{journalcatalog.catalogid}", String.class);
column1Text.setValueExpression("value", ve);
column1.getChildren().add(column1Text);

同样,设置其他数据表列。使用 setValue()HtmlDataTable 对象上设置 ResultSetDataModel 数据集合方法:

dataTable1.setValue(dataModel);

如果 生成错误,则从 action 方法返回错误,该方法将 Facelets 应用程序导航到 <代码 class="literal">error.jsp 使用隐式导航。如果使用隐式导航,则目标 URL 与操作方法返回的 String 值同名。有关隐式导航和其他 JSF 2 功能的更详细讨论,请参阅 JavaServer Faces 2.0,开发人员基本指南参与学习。如果未生成错误,则返回导航到 output.jsp 的输出以显示数据表。 Catalog.java 托管 bean 可在本章下载。

由于我们使用了 @ManagedBean 注解,faces-config.xml 文件是一个空文件,这在必须指定较少配置的条款:

<?xml version="1.0" encoding="UTF-8"?>
<!-- This file is not required if you don't need any extra configuration. -->
<faces-config version="2.0" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xi="http://www.w3.org/2001/XInclude" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=" http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-facesconfig_2_0.xsd">
</faces-config>

下一个屏幕截图中的 jboss-jsf2 项目中显示了托管 bean。 Catalog.java Java 类可能会显示一些错误,这是由于 pom.xml 文件。我们将在后面的部分添加所需的 Maven 依赖项。

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Creating a Facelets template


Facelets 模板 是一个可重用的组件,它包括一个或多个不同的 JSF 页面,模板的部分可用于多个 Facelets 组合页面,因此排除 包含分别构成 Facelets 组合页面的公共部分的每个 JSF 页面。我们将使用 Facelets 模板来包含页眉 JSF 页面和页脚 JSF 页面。 Facelets 模板将在您需要添加的 WEB-INF/templates 目录 中创建templates 目录。右键单击Project Explorer中的WEB-INF文件夹并选择 | 文件夹,如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

New Folder 向导中,选择 webapp | WEB-INF 文件夹并将 文件夹名称 指定为 templates< /code>,如以下屏幕截图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

要创建 Facelets 模板,请选择 文件 | | 其他。在 New 中,选择 JBoss Tools Web | XHTML Page并点击Next,如下图截屏:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

New XHTML Page 向导中,选择 文件夹作为 webapp/WEB-INF/templates 并将 文件名 指定为 BasicTemplate.xhtml 。点击Next,如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Select XHTML Template 中,选择 Common Facelet Page模板,点击Finish,如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

BasicTemplate.xhtml Facelet 模板 WEB-INF/templates 文件夹中创建。在模板中,为 Facelet 合成页面的页眉、内容和页脚部分创建 <div/> 元素。 <ui:insert/> Facelets 标签用作组合页面部分的占位符。由于输入和输出组合页面需要公共的页眉和页脚部分,因此您需要在页眉 div 中包含页眉 JSF 页面,在页脚 <div> 使用 <ui:include/> 标签。为合成页面 包括页面部分。例如,包含一个 header.xhtml JSF 页面,如下所示:

<ui:insert name="header">
  <ui:include src="/WEB-INF/templates/header.xhtml" />
</ui:insert>

我们将在下一节中创建 header.xhtmlfooter.xhtml JSF 页面。 BasicTemplate.xhtml 模板如下:

<!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:ui="http://java.sun.com/jsf/facelets">
  <head>
    <title><ui:insert name="title">JSF 2.0 Facelets</ui:insert></title>
  </head>
  <body>
    <div id="header">
      <ui:insert name="header">
        <ui:include src="/WEB-INF/templates/header.xhtml" />
      </ui:insert>
    </div>
      <div id="content">	
        <ui:insert name="content">
      </ui:insert>
    </div>
    <div id="footer">
      <ui:insert name="footer">
        <ui:include src="/WEB-INF/templates/footer.xhtml" />
      </ui:insert>
    </div>
  </body>
</html>

将清单复制到 Eclipse IDE 中的 BasicTemplate.xhtml 文件。 BasicTemplate.xhtml 文件显示在以下屏幕截图中:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Creating header and footer


在本节中,我们将创建页眉和页脚 JSF 页面。类似于创建 BasicTemplate.xhtml Facelet 模板,创建 header.xhtmlfooter.xhtml WEB-INF/templates 文件夹中。例如,对于标头 JSF 页面,指定 header.xhtml,如下所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Select XHTML Template中创建页眉和页脚的区别,选择Blank JSF Page模板,如下所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

我们将为页眉和页脚部分包含 图形 JPEG 文件。在 header.xhtml 中,使用 h:graphicImageJPEG 文件> 标签包含在 h:panelGrid 标签中。首先,将图形JPEG文件FaceletsHeader.jpgFaceletsFooter.jpg复制到// jboss-jsf2/src/main/webapp 目录。 header.xhtml JSF 页面如下:

<?xml version="1.0" encoding="ISO-8859-1" ?>
<!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:ui="http://java.sun.com/jsf/facelets" xmlns:h="http://java.sun.com/jsf/html" xmlns:f="http://java.sun.com/jsf/core">
  <f:view>
    <h:form>
      <h:panelGrid columns="1">
        <h:graphicImage value="FaceletsHeader.jpg" />
      </h:panelGrid>
    </h:form>
  </f:view>
</html>

同样,在 footer.xhtml JSF 页面中,包含一个 FaceletsFooter .jpg 图像文件,其中 h:graphicImage 标签包含在 h:panelGrid 标签中。 footer.xhtml 页面如下:

<?xml version="1.0" encoding="ISO-8859-1" ?>
<!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:ui="http://java.sun.com/jsf/facelets" xmlns:h="http://java.sun.com/jsf/html" xmlns:f="http://java.sun.com/jsf/core">
  <f:view>
    <h:form>
      <h:panelGrid columns="1">
        <h:graphicImage value="FaceletsFooter.jpg" />
      </h:panelGrid>
    </h:form>
  </f:view>
</html>

jboss-jsf2 项目的目录结构如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Creating input and output Facelets composition pages


在本节中,我们 将创建输入和输出 Facelets 组合页面,input.xhtmloutput.xhtml。创建 Facelets 页面类似于创建 BasicTemplate.xhtmlheader.xhtmlfooter .xhtml 选择要创建的文件夹 input.xhtmloutput.xhtml 作为 webapp。例如,在 Create New XHTML Page 中指定 input.xhtml,为 显示在这里:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Select XHTML Template 中,选择 Form Facelet Page Template 并点击Finish,如下图所示

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

BasicTemplate.xhtml 文件中,我们定义了可以在合成页面中重用的模板结构。 div 标签包含在 header.xhtmlfooter.xhtml< /code> 文件。在 input.xhtml 文件中,使用 ui:composition 包含 BasicTemplate.xhtml 文件 标签的 template 属性。指定 模板的相对路径。我们只需要定义 input.xhtml 合成页面的内容部分。 BasicTemplate.xhtml 文件中的占位符是使用 <ui:insert name="content"/> 指定的。使用 <ui:define name="content"/>input.xhtml 中指定实际定义。在 ui:define 标记中,为输入文本添加 JSF 组件以及相应的输出标签,并添加一个命令按钮以调用托管 bean 中的操作方法 目录。组件使用 EL 表达式与相应的托管 bean 属性绑定 (http://docs.oracle.com/javaee/6/tutorial/doc/gjddd.html)。将 JSF 组件包含在 h:panelGrid 中,该组件包含在 h:form 标记中。 Facelet 合成页面列出如下:

<!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:ui="http://java.sun.com/jsf/facelets" xmlns:h="http://java.sun.com/jsf/html" xmlns:f="http://java.sun.com/jsf/core">
  <ui:composition template="/WEB-INF/templates/BasicTemplate.xhtml">
    <ui:define name="content">
      <h:form>
        <h:panelGrid columns="2">
          <h:outputLabel binding="#{catalog.outputLabel1}" value="SQL Query:" />
          <h:inputText binding="#{catalog.inputText1}" />
        <h:commandButton value="Submit" binding="#{catalog.commandButton1}" action="#{catalog.commandButton1_action}" />
        </h:panelGrid>
      </h:form>
    </ui:define>
  </ui:composition>
</html>

output.xhtml 文件中,包含 BasicTemplate.xhtmltemplate ui:composition 标签的属性。使用 ui:define 标签定义内容部分。在 ui:define 标签内,为数据表添加 h:dataTable 标签。使用 EL 表达式指定与托管 bean 属性 dataTable1 的绑定。用h:dataTable的border属性设置数据表的边框,用rows属性设置行数为5。在 h:dataTable 标签内,为数据表列添加六个 h:column 标签。指定将 h:column 标记绑定到托管 bean 属性。

output.xhtml 页面列出如下:

<!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:ui="http://java.sun.com/jsf/facelets" xmlns:h="http://java.sun.com/jsf/html" xmlns:f="http://java.sun.com/jsf/core">
  <ui:composition template="/WEB-INF/templates/BasicTemplate.xhtml">
    <ui:define name="content">
      <h:form>
        <h:dataTable binding="#{catalog.dataTable1}" border="1" rows="5">
          <h:column binding="#{catalog.column1}"></h:column>
          <h:column binding="#{catalog.column2}"></h:column>
          <h:column binding="#{catalog.column3}"></h:column>
          <h:column binding="#{catalog.column4}"></h:column>
          <h:column binding="#{catalog.column5}"></h:column>
          <h:column binding="#{catalog.column6}"></h:column>
        </h:dataTable>
      </h:form>
    </ui:define>
  </ui:composition>
</html>

有关 关于 JSF 2 特性的更详细讨论,请参阅 JavaServer Faces 2.0,开发人员基本指南 参与学习。添加一个 error.xhtml JSF 页面以显示错误消息。 error.xhtml 页面不是 Facelets 组合页面,只有一个 h:outputLabel 标记与 errorMsg 托管 bean 属性:

<!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:f="http://java.sun.com/jsf/core" xmlns:ui="http://java.sun.com/jsf/facelets">
  <head>
    <title>Error Page</title>
  </head>
  <body>Error Page<h:outputLabel binding="#{catalog.errorMsg}" value="#{catalog.errorMsg}" />
  </body>
</html>

模板 BasicTemplate.xhtml,页眉 header.xhtml,页脚 footer.xhtml< /code> 和 input.xhtmloutput.xhtml 组合页面显示在 项目浏览器标签:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Creating a web descriptor


web 描述符 (web.xml) 在 Java EE 7 中不是必需的,但对于 JSF应用程序,我们需要配置 Facelets servlet。要创建 Web 描述符,请选择 File | | 其他

New 中,选择 JBoss Tools Web | Web Descriptor点击Next,如下图 截图:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

FolderWeb Descriptor File 向导中,单击 < span class="strong">浏览选择一个文件夹。在文件夹选择中,选择WEB-INF文件夹并点击OK,如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

选择WEB-INF文件夹并指定名称web.xml版本 as 3.1 并点击Finish,如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

web.xml 文件在 WEB-INF< 中创建 /代码>文件夹。在 web.xml 中,指定 Faces servlet 及其 servlet 映射。 web.xml Web 描述符如下所示:

<?xml version="1.0" encoding="UTF-8"?>
<web-app version="3.1" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd">
<display-name>JSF 2.x Facelets</display-name>

  <servlet>
    <servlet-name>Faces Servlet</servlet-name>
    <servlet-class>javax.faces.webapp.FacesServlet</servlet-class>
    <load-on-startup>1</load-on-startup>
  </servlet>
  <servlet-mapping>
    <servlet-name>Faces Servlet</servlet-name>
    <url-pattern>*.jsf</url-pattern>
  </servlet-mapping>
  <servlet-mapping>
    <servlet-name>Faces Servlet</servlet-name>
    <url-pattern>*.faces</url-pattern>
  </servlet-mapping>
  <servlet-mapping>
    <servlet-name>Faces Servlet</servlet-name>
    <url-pattern>*.xhtml</url-pattern>
  </servlet-mapping>
  <servlet-mapping>
    <servlet-name>Faces Servlet</servlet-name>
    <url-pattern>/faces/*</url-pattern>
  </servlet-mapping>
</web-app>

web.xml 显示在 以下 jboss-jsf2< /代码>网络项目:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Deploying the web project with Maven


我们创建的Java EE web 项目是基于Maven的。它包括 pom.xml 来构建、编译和打包 Web 应用程序。 WildFly 8.1 中的默认项目是 Java EE 7 版本。由于 Java EE 项目是一个 Web 项目,因此 打包在 war “字面量”>pom.xml。我们在创建 Java EE Web 项目时指定的 Group IdArtifact Id 属性在 pom.xml 也是如此。由于我们使用的是 MySQL 数据库,我们需要添加对 MySQL JDBC 驱动程序的依赖:

<dependency>
  <groupId>mysql</groupId>
  <artifactId>mysql-connector-java</artifactId>
  <version>5.1.22</version>
</dependency>

WildFly 8.1 提供的对 Java EE 7 JSF 2.2 API 的依赖 包含在 pom.xml < /code>默认情况下:

<dependency>
  <groupId>org.jboss.spec.javax.faces</groupId>
  <artifactId>jboss-jsf-api_2.2_spec</artifactId>
  <scope>provided</scope>
</dependency>

由于托管 bean 和 Facelets 组合页面使用 EL 表达式,包括对 el-api 的依赖,WildFly 8.1 默认不提供该依赖:

<dependency>
  <groupId>javax.el</groupId>
  <artifactId>javax.el-api</artifactId>
  <version>3.0.0</version>
</dependency>

CDI (上下文和依赖注入) API, Common Annotations API, JAX-RS API, JPA (Java 持久性 API)、EJB (Enterprise JavaBeans) API、Hibernate Validator API、注释处理器生成 JPA​​ 元模型类、Hibernate 验证器注释处理器和 JUnit API < /a>由WildFly 8.1默认提供,如果没有在本章的示例应用程序中使用,可以删除。在 build 元素中,Compiler 插件和 maven-war-plugin 默认配置。在 maven-war-plugin 插件的配置中,将 WAR 存档的输出目录指定为 deployments 目录。

pom.xml 文件列举如下:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <groupId>org.jboss.jsf2</groupId>
  <artifactId>jboss-jsf2</artifactId>
  <version>1.0.0</version>
  <packaging>war</packaging>
  <name>WildFly JSF 2.x</name>
  <description>A starter Java EE 7 webapp project for use on JBoss WildFly / WildFly, generated from the jboss-javaee6-webapp archetype</description>
  <url>http://wildfly.org</url>
  <licenses>
    <license>
      <name>Apache License, Version 2.0</name>
      <distribution>repo</distribution>
      <url>http://www.apache.org/licenses/LICENSE-2.0.html</url>
    </license>
  </licenses>
  <properties>
    <!-- Explicitly declaring the source encoding eliminates the following message: -->
    <!-- [WARNING] Using platform encoding (UTF-8 actually) to copy filtered resources, i.e. build is platform dependent! -->
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <!-- JBoss dependency versions -->
    <version.wildfly.maven.plugin>1.0.2.Final</version.wildfly.maven.plugin>
    <!-- Define the version of the JBoss BOMs we want to import to specify tested stacks. -->
    <version.jboss.bom>8.1.0.Final</version.jboss.bom>
    <version.arquillian.container>8.1.0.Final</version.arquillian.container>
    <!-- other plugin versions -->
    <version.compiler.plugin>3.1</version.compiler.plugin>
    <version.surefire.plugin>2.16</version.surefire.plugin>
    <version.war.plugin>2.1.1</version.war.plugin>
    <!-- maven-compiler-plugin -->
    <maven.compiler.target>1.7</maven.compiler.target>
    <maven.compiler.source>1.7</maven.compiler.source>
  </properties>
  <dependencyManagement>
    <dependencies>
      <dependency>
        <groupId>org.wildfly.bom</groupId>
        <artifactId>jboss-javaee-7.0-with-tools</artifactId>
        <version>${version.jboss.bom}</version>
        <type>pom</type>
        <scope>import</scope>
      </dependency>
      <dependency>
        <groupId>org.wildfly.bom</groupId>
        <artifactId>jboss-javaee-7.0-with-hibernate</artifactId>
        <version>${version.jboss.bom}</version>
        <type>pom</type>
        <scope>import</scope>
      </dependency>
    </dependencies>
  </dependencyManagement>
  <dependencies>
    <dependency>
      <groupId>mysql</groupId>
      <artifactId>mysql-connector-java</artifactId>
      <version>5.1.22</version>
    </dependency>
    <dependency>
      <groupId>javax.el</groupId>
      <artifactId>javax.el-api</artifactId>
      <version>3.0.0</version>
    </dependency>
    <!-- Import the JSF API, we use provided scope as the API is included in JBoss WildFly -->
    <dependency>
      <groupId>org.jboss.spec.javax.faces</groupId>
      <artifactId>jboss-jsf-api_2.2_spec</artifactId>
      <scope>provided</scope>
    </dependency>
  </dependencies>
  <build>
    <!-- Maven will append the version to the finalName (which is the name given to the generated war, and hence the context root) -->
    <finalName>${project.artifactId}</finalName>
    <plugins>
      <!-- Compiler plugin enforces Java 1.6 compatibility and activates annotation processors -->
      <plugin>
        <artifactId>maven-compiler-plugin</artifactId>
        <version>${version.compiler.plugin}</version>
        <configuration>
          <source>${maven.compiler.source}</source>
          <target>${maven.compiler.target}</target>
        </configuration>
      </plugin>
      <plugin>
        <artifactId>maven-war-plugin</artifactId>
        <version>${version.war.plugin}</version>
        <configuration>
          <outputDirectory>C:\wildfly-8.1.0.Final\standalone\deployments</outputDirectory>
          <!-- Java EE 7 doesn't require web.xml, Maven needs to catch up! -->
          <failOnMissingWebXml>false</failOnMissingWebXml>
        </configuration>
      </plugin>
      <!-- The WildFly plugin deploys your war to a local WildFly container -->
      <!-- To use, run: mvn package wildfly:deploy -->
      <plugin>
        <groupId>org.wildfly.plugins</groupId>
        <artifactId>wildfly-maven-plugin</artifactId>
        <version>${version.wildfly.maven.plugin}</version>
      </plugin>
    </plugins>
  </build>
</project>

右键单击 pom.xml 文件并选择运行方式 | Maven 安装,如下图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Maven pom.xml build BUILD SUCCESS message,如下图所示。 jboss-jsf2 应用程序被编译、打包并复制到 deployments 文件夹,就像所有 deployments 目录的 >WAR 档案会自动安装,jboss-js2.war 会部署到 WildFly 8.1 .

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

使用 URL Adminstration Console ="literal">http://localhost:8080/jboss-jsf2.war 归档被列为已部署,如以下屏幕截图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Running the Facelets application


在这个 部分,我们将在 WildFly 8 上运行 JSF 2 应用程序。调用 input.xhtml 文件使用 URL http://localhost:8080/jboss-jsf2/input.xhtmljboss-jsf2 包含在内,因为它是 jboss-jsf2.war 应用程序的上下文根。使用模板将页眉和页脚图形 JPEG 文件包含在 Facelets 组合页面中。指定一个 SQL 查询,例如 SELECT * FROM CATALOG 并点击 Submit,如图在以下屏幕截图中:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

input.xhtml 页面 调用 Facelets Servlet 作为 .xhtml< /code> 在 servlet 映射中指定。托管 bean 的 action 方法生成 JSF 数据表并返回输出,该输出呈现 output.xhtml。浏览器中显示的 URL 保持不变,因为请求调度程序发送请求转发,这不会启动新请求。要在浏览器 URL 中显示 output.xhtml 文件,需要重定向,这会启动新请求。使用模板将相同的页眉和页脚包含在 output.xhml 文件中,如以下屏幕截图所示:

读书笔记《advanced-java-ee-development-with-wildfly》开发JSF 2.x Facelets

Summary


在本章中,我们创建了一个 JSF 2.x 应用程序来从 SQL 查询创建数据表。我们使用基于 Facelets 的模板来包含相同的页眉和页脚。使用 Maven 构建工具编译和打包 JSF 2.0 应用程序并部署到 WildFly 8.1。 Facelets 应用程序在浏览器上运行以生成数据表。

在下一章中,我们将讨论在 WildFly 8.1 中使用 Ajax。