使用 Eclipse、Web Tools Platform (WTP) for Eclipse、Derby 和 Jakarta-Tomcat 构建动态 Web 应用程序是件很容易的事。本文将带您学习如何安装和配置所有这些必需的开放源码组件,并使用 JSP 和 servlet 构建一个完整的用于向 Derby 数据库存储和获取信息的 Web 应用程序。
Eclipse 是使用 Java 技术开发 Web 应用程序的理想平台。动态 Web 应用程序的 3 层设计非常适合与运行在 servlet 容器(例如 Apache Jakarta Tomcat)中的 JSP 和 Servlet 相结合。持久数据层可以适当地由 Derby 数据库提供。用于开发 J2EE 和 Web 应用程序的 Eclipse Web Tools Platform (WTP) 项目工具集,加上 Derby Eclipse 插件,可以提供快速而简便的 Web 开发。
本文讨论 WTP 提供的一些功能、Derby 数据库插件以及一个完整的示例应用程序,该应用程序使用了 JSP、JavaServer Pages Standard Tag Library (JSTL) 和 Servlets。这个示例应用程序是一个虚拟的、经过简化的航线机票预订系统。
为了更好地利用本文,您应该理解 JSP、JSTL 和 Servlet 技术的基本知识,理解简单的 SQL,并对 Eclipse 有一定的了解。本文中还使用了 WTP 的一些特性,但本文不是关于 WTP 工具的全面教程。要了解更多关于这些主题方面的知识,请参考本文最后给出的 参考资料 列表。如果您已经知道 WTP 的一些背景,并且想直接开始下载所有必需的软件,那么请略过 软件需求 小节。否则,请阅读下一小节,以了解 WTP 是什么,以及如何在 Eclipse 中使用其中一些组件来开发示例应用程序。
IBM Cloudscape 是 Apache Derby 开放源码数据库的商业发行版。如果没有引用特定的文件或名称,那么这两个名称在本文中可以互换使用。
![]() ![]() |
![]()
|
Eclipse Web Tools Platform (WTP) 项目允许 Eclipse 用户开发 J2EE Web 应用程序。这个平台中包括了多个编辑器、图形编辑器、特性、构建器、一个 Web 服务向导、数据库访问和查询工具以及其他组件。该项目提供了大量的工具。而在使用 Derby 作为后台数据库构建一个 Web 应用程序时,只会演示其中有限的几种工具。
在 www.eclipse.org/webtools 上 WTP 的特许权定义如下:“... 构建有用的工具和一个通用的、可扩展的且基于标准的工具平台,在这个平台上,软件供应商可以创建用于产生支持 Web 的应用程序的专门的、不同的解决方案。”本文不讨论为这个平台构建新的工具,而是使用它作为一个开放的平台,以便使用开放源码组件构建 Web 应用程序。
Web Standard Tools 和 J2EE Standard Tools
WTP 分为两个子项目,Web Standard Tools 和 J2EE Standard Tools。Web Standard Tools (WST) 项目为多层 Web 应用程序提供公共基础设施。它提供了一个服务器视图,使您可以发布在 Eclipse 中创建的资源,并且在一个服务器上运行它们。WST 不包括用于 Java 语言的特定工具,也不包括用于特定于 Web 框架的技术的特定工具。
J2EE Standard Tools (JST) 项目提供工具,用于简化包括 EJB、Servlet、JSP、JDBC、 Web 服务等等在内的 J2EE API 的开发。J2EE Standard Tools 项目以 Web Standard Tools 项目提供的 Server Tools 支持为基础,包括 servlet 和 EJB 容器。
下一节讨论在构建和运行示例应用程序时所需的软件组件。
![]() ![]() |
![]()
|
示例应用程序使用了以下软件组件和技术:
- Eclipse
- 使用 IDE 编写和运行示例应用程序。它是开发和构建 Java 应用程序的基础。
- 使用 Eclipse 附带的 Java Development Tools (JDT) 编译属于应用程序一部分的 Java 类。
- WTP
- 使用编辑器创建 JSP 文件。该编辑器包括 JSP 语法的内容辅助。
- 使用 Servers 视图启动和停止外部的 Jakarta Tomcat servlet 引擎。
- 使用 J2EE 透视图创建动态 Web 应用程序,这个动态 Web 应用程序装配和配置 J2EE Web 应用程序,包括与所有 J2EE Web 应用程序相同的标准结构和部署描述符。
- 通过 Database Explorer 视图创建一个到 Derby 数据库的连接。
- Derby 插件
- 添加 Derby 特性到动态 Web 项目,以便将 JAR 文件包括在项目中。
- 在应用程序开发期间启动和停止 Derby 网络服务器。
- 使用 ij SQL 查询工具运行 SQL 查询。
- 将项目的 derby.system.home 属性设置为指向数据库。
- JavaServer Pages Standard Tag Library (JSTL)
- 这个标记库使基于 JSP 的应用程序可以使用一个标准标记库来执行常见的任务。示例应用程序使用这些标记来执行诸如迭代和数据库访问之类的任务。在 JSP 中还使用了 EL(Expression Language,表达式语言),这是一种脚本语言。
- Apache Jakarta Tomcat servlet 引擎
- 运行由 JSP 和 Servlet 组成的 Web 应用程序。
- 提供对 Servlet 2.4 和 JSP 2.0 API 的支持,包括对 EL 的支持。
- 提供对在 Web 应用程序的部署描述符中将 Derby 数据库定义为一个 Data Source 的支持。
![]() ![]() |
![]()
|
本节中描述的软件可以免费下载,在运行例子和构建示例 Web 应用程序之前,必须安装这些软件。
以下两种 Java 开发工具箱 之一:
- IBM SDK version 1.4.2 或更高版本。
- Sun JDK version 1.4.2 或更高版本。
Eclipse 和 WTP。您可以下载一个包括 Eclipse SDK、所有 WTP 先决条件以及 WTP 本身的 zip 文件。在 Windows 上,这个文件的文件名为 wtp-all-in-one-0.7-win32.zip。如果您喜欢下载 Linux 上的版本,那就是 wtp-all-in-one-0.7-linux-gtk.tar.gz 文件。您可以从 eclipse.org 下载其中任何一个文件(见 参考资料)。
如果您已经安装了 Eclipse,或者安装了 WTP 的一些先决条件,那么您可以比较下面列出的 wtp-all-in-one zip 文件中包含的插件版本。而且, Download 页面也列出了 0.7 WTP 的先决条件,所以您要确保安装的组件至少能跟上这里列出的版本。如果可供下载的版本不同于下面列出的版本,那么请下载 WTP 站点上建议的版本。
- Eclipse 3.1, for Windows:eclipse-SDK-3.1-win32.zip
- EMF SDK:emf-sdo-xsd-SDK-2.1.0.zip
- GEF SDK:GEF-SDK-3.1.zip
- Java EMF Model Runtime:JEM-SDK-1.1.zip
- Web Tools Platform:wtp-0.7.zip
Derby 数据库 Eclipse 插件(apache.org 提供了 zip 文件,见 参考资料)。Apache Derby 数据库最近发布了数据库引擎的 10.1 版。为了在 Eclipse 3.1 上运行,需要以下版本的插件:
- Derby Core 插件,Version 10.1.1
- Derby UI 插件,Version 1.1.0
Apache Jakarta Tomcat。下载 Version 5.0.28 (见 参考资料) 。
JavaServer Pages Standard Tag Library (JSTL)。从 Apache Jakarta Project 下载 Standard 1.1 Taglib,jakarta-taglibs-standard-1.1.2.zip(见 参考资料)。
示例应用程序源代码和 WAR 文件:
- WAR 文件就是 Web Application Archive,它是打包和部署 J2EE Web 应用程序的标准单元。所有遵从 J2EE 的 servlet 容器都接受 WAR 文件,并且可以部署这些文件。请下载 LowFareAir.war 文件到您的文件系统中(见 下载)。
- 下载 zip 文件 LowFareDataSQL.zip,该文件包含 Derby 数据库和访问 airlinesDB 数据库的示例 SQL 文件(见 下载)。
![]() ![]() |
![]()
|
下载了所有必需的软件之后,便需要配置它们,以便可以构建应用程序。
如果还没有安装 1.4.2 或更高版本的 JDK,那么安装它。这里需要的是 JDK,而不是 JRE。
通过将 wtp-all-in-one-0.7-win32.zip 解压到一个您想放置 Eclipse 的目录中,便可以安装 Eclipse。如果已经安装了 Eclipse,并且您下载了前面列出的各个组件,那么将那些组件解压到 Eclipse 主目录,因为它们都是插件,这些组件将安装到 Eclipse 的插件目录。
将 Jakarta Tomcat 解压或安装到与 Eclipse 安装目录不同的一个目录。
现在需要配置 Eclipse,以便在使用 WTP 的 Eclipse 中运行 Tomcat 作为服务器。为此:
- 访问 http://www.eclipse.org/webtools/ 并选择 WTP Community 下的教程链接。
- 在 Tutorials 页面,选择名为“Building a School Schedule Web Application”的教程。
- 遵循该教程“Installing the Tomcat Runtime in Eclipse”小节中的所有说明。对于这个示例 Web 应用程序,不需要完成整个教程。
将两个文件(Derby Core 和 UI 插件的 zip 文件)都解压到 Eclipse 主目录下的插件目录。Derby 插件附带了关于如何使用这些插件的所有功能的完整的教程和例子。为了访问帮助,请选择 Help > Help Contents > Derby Plug-ins User Guide。
![]() ![]() |
![]()
|
LowFareAir Web 应用程序遵从标准的 3 层设计模型,由表示层、业务逻辑和控制层和数据或持久层组成。JSP 包括 JSTL 标记库,提供了 UI 或表示层。Servlets 和 java 支持类提供应用程序的业务逻辑和流控制。而 Derby 数据库及 JavaBeans 则提供数据层。下面的图说明了这一点。
图 1. 示例应用程序设计
![应用程序设计](https://i-blog.csdnimg.cn/blog_migrate/bd0d48c5229ddfaa1745418307af7af4.png)
以 JSP 表示的表示层通常不应该直接与数据层交互,因此也不应该进行数据库查询。该应用程序的设计遵从公认的范例,只有第一个 JSP 除外。为了快速开发原型,将数据库访问合并到视图层, 打破数据与视图严格分离的限制,这是可以接受的。第一个 JSP,即 Welcome.jsp, 使用 JSTL SQL 库从该页面发出一个 SQL 查询,因而同时占据了表示层和数据层。
其他 JSP 仅仅充当表示层,它们将所有的数据处理任务都递交给 Servlet,由这些 Servlet 与 Derby 数据库交互。如果您有兴趣在将来的 Web 应用程序的原型开发中使用这种方法学,那么这里展示了一个 JSTL SQL 库的例子,但是对于生产环境,不建议这么做。
![]() ![]() |
![]()
|
这个示例应用程序允许新用户的注册,并允许已有用户登录到这个应用程序。用户登录以后,应用程序展示出很多的航班,以供用户订票。由于只提供直达航班,所以要检查用户所选的航班,看出发地与目的地之间是否有直达航班。如果有这样的航班,那么用户就可以选择预订这个航班的机票。最后,用户可以看到通过 LowFare Air 预订的所有航班的历史记录。
示例应用程序的流程由以下步骤组成:
- 用户注册或验证
- 用于应用程序这一部分的 JSP 是 Welcome.jsp、Login.jsp 和 Register.jsp。
- LoginServlet 担任控制器 —— 或者在 Derby 数据库的 APP.USERS 表中验证用户的名称,或者将用户的名称插入到这个表中。
- 注册成功之后,设置一个持久的 cookie;登录成功后,将客户机的用户 ID 添加到会话中。
- 检索和选择航班
- Welcome.jsp 用于选择航班,而 GetFlights.jsp 则用于检索航班。
- CheckFlightsServlet 担任控制器。如果在选择的两个城市之间存在航班,那么将航班信息传递给 GetFlights.jsp。否则,让用户返回到 Welcome.jsp 页面,以便选择其他航班。
- 如果有航班,那么 DerbyDatabase 类将从数据库检索到的航班信息放入到名为 FlightsBean 的 JavaBean 中。
- 通过更新 Flight History 预订用户的航班
- 这里使用的 JSP 是 BookFlights.jsp 和 GoodBye.jsp。BookFlights.jsp 请求用户对他们预订的航班作最后的确认。GoodBye.jsp 显示用户通过 Derby Airlines 预订的所有航班。
- UpdateHistoryServlet 以用户名和用户刚预订的航班更新 APP.FlightHistory 表。然后请求被重定向到 GoodBye.jsp。
- 用户退出
- 应用程序的最后阶段是退出应用程序,或者预订其他航班。这里使用的 JSP 是 LoggedOut.jsp,或者,如果用户还想预订其他的航班,则使用 Welcome.jsp。
- 如果用户选择退出,则从 Session 对象中删除用户 ID。因此,当该用户下一次重返站点时,虽然保留了一个持久 cookie,但用户 ID 不在 Session 对象中,因此用户必须再次登录。
下面的图生动地展示了这一流程。
图 2. 示例应用程序的流程
![应用程序流程](https://i-blog.csdnimg.cn/blog_migrate/dd3feaff34136d42d9754efa37de1144.png)
![应用程序流程](https://i-blog.csdnimg.cn/blog_migrate/b3269c61dacfc668509e04802a509b7f.png)
![应用程序流程](https://i-blog.csdnimg.cn/blog_migrate/2e0c36cd7c0df29e936d4b437a288f49.png)
![应用程序流程](https://i-blog.csdnimg.cn/blog_migrate/7396b84dfacb55d79aa5648190e412c9.png)
![]() ![]() |
![]()
|
为了理解如何使用随 WTP 附带的不同工具以及 Derby 插件,请将应用程序作为 WAR 文件导入,WAR 是 Web 应用程序的标准打包单元,其文件格式为 JAR。
构建任何使用 JSP 或 Servlet 的 Web 应用程序的第一步是创建一个动态 Web 应用程序。您可以使用 WTP 的一组工具创建这样一个动态 Web 应用程序,它将为 J2EE Web 应用程序自动创建适当的目录结构。将 WAR 文件导入到 Project Explorer 视图的 Dynamic Web Project 文件夹中,以便创建一个新的 Web 项目。
启动 Eclipse,遵循以下步骤导入 WAR 文件,以创建一个新的动态 Web 项目:
- 打开 J2EE 透视图。
- 在 Project Explorer 视图中,右键单击 Dynamic Web Projects 文件夹。
- 选择 Import,然后在 Import 窗口中,选择 WAR file 并单击 Next。
- 在 WAR Import 窗口中,浏览到早先下载的 LowFareAir.war 文件(见前面的 软件需求)。将项目命名为
LowFareAir
,并确保 Target server 是 Apache Tomcat V5.0(这是您早先作了配置的,见前面的 软件配置)。单击 Finish。
图 3 展示了这个过程的最后一步。
图 3. 导入 WAR 文件以创建动态 Web 项目
![动态 Web 项目](https://i-blog.csdnimg.cn/blog_migrate/c292a9bc1eb5da56eb62ba286aa79542.png)
您还需要导入三个上述 WAR 文件中没有的 JAR 文件:jstl.jar 和早先下载的 Jakarta taglibs 包中的 standard.jar,以及 Derby 核心插件中的 derbyclient.jar 文件。通常,一个完整的 WAR 文件会包括这些 JAR 文件,但出于演示的目的,您应该知道如何将它们导入到动态 Web 项目中。
为了获得 Jakarta 包中的这几个 JAR 文件,请解压 jakarta-taglibs-standard-1.1.2.zip 文件。jstl.jar 和 standard.jar 文件在新创建的 jakarta-taglibs-standard-1.1.2/lib 目录中。为了导入这几个 JAR 文件:
- 打开 Dynamic Web Projects 文件夹。这时将出现刚才导入的 LowFareAir 项目。展开这个文件夹,然后展开 WebContent 文件夹。
- 右键单击 WebContent/WEB-INF/lib 文件夹并选择 Import。在 Import 窗口中,选择 File System,然后单击 Next。
- 浏览至子目录 jakarta-taglibs-standard-1.1.2/lib,您曾经将 taglibs 解压至该目录,然后选择 jstl.jar 和 standard.jar。确保导入到 LowFareAir/WebContent/WEB-INF/lib 目录。然后单击 Finish。
现在需要将 derbyclient.jar 文件添加到 Web 应用程序可用的库中。您的 Web 应用程序将使用 derbyclient.jar 中的 JDBC 来建立到数据库的连接。
为了导入 derbyclient.jar:
- 右键单击 WebContent/WEB-INF/lib 文件夹并选择 Import。在 Import 窗口中,选择 File System,然后单击 Next。
- 浏览至 Eclipse 主目录下的插件目录,然后打开 org.apache.derby.core_10.1.1 目录。选择 derbyclient.jar。确保导入到 LowFareAir/WebContent/WEB-INF/lib 目录。然后单击 Finish。
这样便完成了 Web 组件的导入,包括 Java 源文件和用于应用程序的所有库。接下来,导入装有示例数据的 Derby 数据库 airlinesDB
。
![]() ![]() |
![]()
|
为了配置数据层以及应用程序用于访问数据库的工具:
- 将 Apache Derby Nature 添加到 LowFareAir 项目中。
- 将 LowFareAirData.zip 文件导入到项目中。该 zip 文件包含
airlinesDB
Derby 数据库,其中包含所有用于应用程序的数据以及一些示例 SQL 脚本。 - 配置 Web 应用程序部署描述符 web.xml,以包含一个指向
airlinesDB
数据库的数据源。 - 将 Derby 属性
derby.system.home
设置为指向airlinesDB
数据库的完整路径。通过设置这个属性,在 JDBC 连接 URL 中所有对airlinesDB
数据库的引用都只需引用“airlinesDB”,而不必引用完整的文件系统路径。
该 Web 应用程序使用一个 Derby 数据库来为虚拟的 LowFareAir 航空公司存储和查询航班信息。在 Eclipse 中访问和使用 Derby 数据库的一种简便方法是通过 Derby 插件。
Derby 插件允许添加 Derby 特性到任何 Eclipse 项目中。将一种特性添加到一个项目(包括动态 Web 项目),意味着该项目将“继承”某些功能和行为。而添加 Derby 特性则意味着将与 Derby 捆绑的 Derby 数据库 JAR 文件和命令行工具添加到 Eclipse 环境中。
Project Explorer 视图现在将显示刚才创建的 LowFareAir 项目。
为了添加 Derby 特性到 LowFareAir 项目中,在它上面单击右键并选择菜单项 Apache Derby > Add Apache Derby nature。
源代码中包括了 airlinesDB
,这是用于 Web 应用程序的示例数据库。这个数据库和其他一些示例 SQL 都需要导入到 LowFareAir 项目中。为此:
- 展开 Dynamic Web Projects 文件夹。右键单击 LowFareAir 文件夹并选择 Import。在 Import 窗口中,选择 Archive file,然后单击 Next。
- 浏览至 LowFareAirData.zip,确保选择了左框中的 / 目录。这里包括 data 和 sql 文件夹。选择 LowFareAir 作为 Into 文件夹的名称。然后单击 Finish。
- 如果导入成功,LowFareAir 文件夹应该包含两个新的子文件夹:data 和 sql。data 文件夹将包含 airlinesDB 目录(数据库)。
- sql 目录包含三个 SQL 文件,分别是 airlinesDB.sql、flights.sql 和 flighthistory_users.sql。
现在 Web 应用程序所需的所有文件都已导入完毕,LowFareAir 项目的结构现在看上去应该如图 4 所示。
图 4. LowFareAir 项目的 Project Explorer 视图
![LowFareAir 项目的 Project Explorer 视图](https://i-blog.csdnimg.cn/blog_migrate/5fb87ecf2cf88046ad0c600095f6fa21.png)
web.xml 文件包含关于使用 Derby airlinesDB 数据库作为数据源的一个数据源条目。并不是每个连接到 Derby 数据库的 Web 应用程序都需要如此。但是为了演示的目的,这个应用程序为第一个 JSP 页面使用一个数据源。其他 JSP 不使用这个数据源,而 Servlet 使用一个标准的 Java 类,该类使用 JDBC 连接到数据库。
为了确定 airlinesDB 在文件系统上的位置,右键单击 LowFareAir 项目的 data 目录下的 airlinesDB 文件夹,选择 Properties。Properties 窗口显示一个 Location 字段,其中有指向 airlinesDB 目录的完整文件系统路径。复制这个字符串,以便在下一步中使用。例如,这个路径可能类似于 C:/eclipse/workspace/LowFareAir/data/airlinesDB。
打开 web.xml(在 WebContent/WEB-INF 目录下),在以 Source 模式查看时浏览至下面这一段(为了提高可读性,param-value 部分中的条目加入了换行符,但是 URL 应该是连续的一行):
清单 1. Web.xml context-param 部分
<context-param> <param-name>javax.servlet.jsp.jstl.sql.dataSource</param-name> <param-value> jdbc:derby://localhost:1527/C:/eclipse/workspace/LowFareAir/data/ / airlinesDB;user=a;password=b;, org.apache.derby.jdbc.ClientDriver </param-value> </context-param> |
使用刚才复制的 airlinesDB
数据库的完整路径,将 <param-value> 部分中的值改为您环境中的数据库 URL。如果这个路径不正确,应用程序的第一个页面(Welcome.jsp)将失败。而且,在运行 Welcome.jsp 之前,需要启动网络服务器,因为前面显示的 URL 尝试使用 Derby Client 驱动程序访问网络服务器。
在 Eclipse 中配置 Derby 数据库环境的下一步是编辑名为 derby.system.home
的 Derby 系统属性,使之指向 airlinesDB
数据库的位置。这样您便可以使用 Derby 插件连接到 airlinesDB
,而不必指定到数据库的完整文件系统路径。在数据库连接 URL 中只需列出名称 airlinesDB
。
使用之前复制的 airlinesDB 目录的路径设置 derby.system.home
,只需做少量修改。
- 右键单击 LowFareAir 项目并选择 Properties。
- 在 Properties 窗口的左侧(当前它提示 PropertyDialog.propertyMessage —— 看来是一个 bug)选择 Apache Derby。
- 在右侧是 Apache Derby 属性,您可以更改该属性。名为
derby.system.home
的 Derby System 属性当前被设为默认值(.)。将其改为指向 airlinesDB 目录所在目录的完整路径。注意:您也可以在port
属性中修改网络服务器所侦听的端口。
编辑derby.system.home
属性的值,将其设置为 data 目录的完整路径。粘贴您之前复制的字符串,然后去掉后面的 /airlinesDB。所以,derby.system.home 属性将成为:C:/eclipse/workspace/LowFareAir/data。注意:不要输入数据库目录本身的名称 —— 它应该是数据库目录所在的目录,在这里就是 data 目录,而不是 airlinesDB 目录本身。 - 最后单击 OK 保存对项目的设置。
接下来您将启动 Derby Network Server,建立到 airlinesDB 数据库的连接,并使用随 Derby 插件附带的 ij 工具发出 SQL。
由于您要对 airlinesDB 中的表运行一些查询,所以有必要知道有哪些表,这些表是如何定义的。下面就显示了这些表。SQL 文件 airlinesDB.sql 用于创建数据库。不要再次运行 airlinesDB.sql,除非您删除了旧的数据库,并希望在一个新的数据库中重新创建所有的表。
清单 2. 在 airlinesDB 数据库中创建表的语句
CREATE TABLE APP.CITIES ( CITY_ID INTEGER NOT NULL constraint cities_pk primary key, CITY_NAME VARCHAR(24) NOT NULL, COUNTRY VARCHAR(26) NOT NULL, AIRPORT VARCHAR(26), LANGUAGE VARCHAR(16), COUNTRY_ISO_CODE CHAR(2) ); CREATE TABLE APP.FLIGHTS ( FLIGHT_ID CHAR(6) NOT NULL, SEGMENT_NUMBER INTEGER NOT NULL, ORIG_AIRPORT CHAR(3), DEPART_TIME TIME, DEST_AIRPORT CHAR(3), ARRIVE_TIME TIME, MEAL CHAR(1) CONSTRAINT MEAL_CONSTRAINT CHECK (meal IN ('B', 'L', 'D', 'S')), FLYING_TIME DOUBLE PRECISION, MILES INTEGER, AIRCRAFT VARCHAR(6), CONSTRAINT FLIGHTS_PK Primary Key (FLIGHT_ID, SEGMENT_NUMBER) ); CREATE TABLE APP.FLIGHTAVAILABILITY ( FLIGHT_ID CHAR(6) NOT NULL , SEGMENT_NUMBER INTEGER NOT NULL , FLIGHT_DATE DATE NOT NULL , ECONOMY_SEATS_TAKEN INTEGER DEFAULT 0, BUSINESS_SEATS_TAKEN INTEGER DEFAULT 0, FIRSTCLASS_SEATS_TAKEN INTEGER DEFAULT 0, CONSTRAINT FLIGHTAVAIL_PK Primary Key (FLIGHT_ID, SEGMENT_NUMBER, FLIGHT_DATE), CONSTRAINT FLIGHTS_FK2 Foreign Key (FLIGHT_ID, SEGMENT_NUMBER) REFERENCES FLIGHTS (FLIGHT_ID, SEGMENT_NUMBER) ); CREATE TABLE APP.FLIGHTHISTORY ( ID INTEGER NOT NULL GENERATED ALWAYS AS IDENTITY, USERNAME VARCHAR(26) NOT NULL, FLIGHT_ID CHAR(6) NOT NULL, ORIG_AIRPORT CHAR(3) NOT NULL, DEST_AIRPORT CHAR(3) NOT NULL, BEGIN_DATE CHAR(12), CLASS CHAR(12) ); CREATE TABLE APP.USERS ( ID INTEGER NOT NULL GENERATED ALWAYS AS IDENTITY, USERNAME VARCHAR(40) NOT NULL, PASSWORD VARCHAR(20) ); |
现在右键单击 LowFareAir 项目并选择 Apache Derby > Start Derby Network Server,从而启动 Derby 网络服务器。控制台视图应该会表示,服务器准备在 Derby 属性 Network Server 设置中指定的端口上接受连接。打开 sql 文件夹并右键单击 flights.sql 文件。选择 Apache Derby > Run SQL Script using 'ij'。
控制台窗口将显示 flights.sql 文件中包含的三条 SQL 语句的输出。 如果没有成功建立连接,那么检查网络服务器是否已经启动,以及 derby.system.home
是否被设为 LowFareAir 文件夹下 data 目录的完整路径。
![]() ![]() |
![]()
|
WTP 有一组丰富的数据库工具,允许用户连接到 Derby、DB2、Informix、MySql、Oracle、SQL Server 和 Sybase 数据库,浏览这些数据库,以及对这些数据库发出 SQL。在本节中,您将连接到使用 Derby Network Client 驱动程序的 Derby Network Server,并学习如何使用 WTP 的一些工具作为使用 Derby 插件的替代方案。
在 J2EE 透视图中,选择 Window > Show View > Other。在 Show View 窗口中,选择 Data > Database Explorer 然后单击 OK。Database Explorer 视图将出现在工作区的右下端。在此视图中单击右键,并选择 New Connection。
这时将出现 New Connection 向导。取消对 Use default naming convention 复选框的选择,并将连接命名为 Derby 10.1。在 Select a database manager 区域,展开树中的 Derby 项。注意,它列出 10.0 版的数据库系统。
WTP 0.7 只直接支持 Derby 10.0,但是,最新版本的 Derby 是 10.1 版,而且您将在这里与 Database Explorer 一起使用的 Derby JAR 文件是 10.1 版。在 10.1 版的 Derby 中,建议采用一种新的开放源码客户机驱动程序 —— derbyclient.jar —— 来连接到网络服务器。
下图展示了在我的环境中每个字段的值。下面的表还列出了示例设置。
图 5. WTP Database Explorer 的 New Connection 向导
![创建一个新连接](https://i-blog.csdnimg.cn/blog_migrate/7d2bf10f195cc5fd82e331cf66c47aac.png)
参数 | 值 |
---|---|
Connection Name | Derby 10.1 |
Database manager | Derby 10.0 |
JDBC driver | Other |
Database | C:/eclipse/workspace/LowFareAir/data/airlinesDB |
JDBC driver class | org.apache.derby.jdbc.ClientDriver |
Class location | C:/eclipse/plugins/org.apache.derby.core_10.1.1/derbyclient.jar |
Connection URL | jdbc:derby://localhost:1527/C:/eclipse/workspace/LowFareAir/data/airlinesDB |
User ID | slc (any non-empty value) |
Password | slc (any non-empty value) |
对 Derby 数据库是可以配置认证的,但是这里还没有为 airlinesDB 数据库设置认证。使用任意(非空)值作为用户 ID 和密码,并单击 Test Connection 按钮。如果网络服务器在端口 1527 上运行,那么测试应该可以成功。否则,确保网络服务器在连接 URL 指定的端口上运行,并确保所有的值都适合您的环境。
由于网络服务器是用来连接到 airlinesDB
数据库的,因此可以由多个 JVM 访问它。这意味着 ij、Database Explorer 和 Eclipse 外部的客户机应用程序都可以连接和查询该数据库中的表。
测试连接成功之后,单击 Next 按钮。
在 Specify Filter 窗口中,取消对 Disable filter 复选框的选择,选择 Selection 并选择 APP 模式。然后单击 Finish。
图 6. 为 Derby 10.1 连接指定过滤器
![指定过滤器](https://i-blog.csdnimg.cn/blog_migrate/8336cf0e098ed9db1347f8c2b0985e85.png)
现在,Database Explorer 视图显示到 airlinesDB
数据库的连接。展开树,浏览至 APP 模式的 Tables 文件夹下的 FLIGHTS 表。右键单击 FLIGHTS 表,并选择 Data > Sample Contents。
图 7. Database Explorer 中的示例连接
![Database Explorer 中的示例连接](https://i-blog.csdnimg.cn/blog_migrate/0fa690446b4f7bc61ba6a9616f31a335.png)
现在将出现 Data Output 视图,其中包含 FLIGHTS 表中的行。
图 8. Data Output 视图
![FLIGHTS 表的 Data Output 视图](https://i-blog.csdnimg.cn/blog_migrate/6df955ca75b250f89a9e8fa349913ea4.png)
Database Explorer 视图的另一个特性是可以插入、删除和更新表中的行。Table Editor 提供了修改表中数据的能力。如果您想添加另一行到 FLIGHTS 表中,在 Database Explorer 视图中右键单击这个表,选择 Data > Open。输入一个新的行,在每个列中提供如下所示的值。注意 FLIGHTS 选项卡上单词 FLIGHTS 之前的那个星号。这表明,自上次保存以来,编辑器已经被修改。
图 9. Table Editor
![Table Editor 中的 FLIGHTS 表](https://i-blog.csdnimg.cn/blog_migrate/77346b9e4f933dbf76e50ad5aa940682.png)
为了插入行到表中,选择 File > Save 或使用快捷键 Ctrl + S 保存编辑器。Data Output 视图的 Messages 选项卡显示数据插入成功。
图 10. 成功地插入一行到 FLIGHTS 表中
![Data Output 视图显示成功地插入一行到 FLIGHTS 表中](https://i-blog.csdnimg.cn/blog_migrate/d5ed90b444858ebeabef0ff91c7890b5.png)
Database Explorer 视图的其他特性包括抽取和下载表的能力、打开 SQL Editor 以发出即席 SQL,以及 Generate DDL 选项,该选项在生成用于创建整个数据库模式或模式的一个子集的 SQL 脚本时十分有用。您可以通过在模式对象(表、视图、索引或模式)上单击右键自己探索这些选项,看看对于特定的对象有哪些可用的选项。
![]() ![]() |
![]()
|
现在可以开始查看应用程序中的 JSP。参考 图 2 中的应用程序流程,第一个 JSP 页面是 Welcome.jsp。在 Project Explorer 中,打开 WebContent 文件夹下的 Welcome.jsp 文件。下面的小节中将展示这个页面的代码。注意:有些代码清单有反斜杠字符“/”,这表示代码行是连续的,但为了可读性,这里对其格式作了调整。
清单 3. 在 Welcome.jsp 中导入 Core 和 SQL 标记库
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%> <%@taglib uri="http://java.sun.com/jsp/jstl/sql" prefix="sql"%> |
前两行包括可用于 JSP 页面的 taglib 指令,这样便可以使用 core 和 SQL JSTL 标记库。
接下来这一段使用 core 标记库来测试在用户浏览器中是否设置了 cookie。如果没有 cookie,那么将 JSP 页面重定向到 Register.jsp。如果至少有一个 cookie,那么检查是否设置了名为 derbyCookie 的 cookie。如果存在 derbyCookie,那么接下来的测试是检查 Session 对象是否包含一个用户 ID。如果没有包括用户 ID,那么用户进入 Login.jsp 页面,以登录到应用程序。
如果用户在 Session 对象中有用户 ID,那么用户可以继续,处理仍停留在 Welcome.jsp 页面。
清单 4. 测试 Welcome.jsp 中是否设置了 cookie
<HTML> <HEAD> <TITLE>Derby Airlines</TITLE> </HEAD> <BODY> <c:choose> <c:when test="${empty cookie}"> <jsp:forward page="Register.jsp" /> </c:when> <c:otherwise> <!-- if the derbyCookie has been set but the username is not in / the session object --> <c:forEach var="cookieVal" items="${cookie}"> <c:if test="${cookieVal.key == 'derbyCookie'}"> <c:if test="${empty sessionScope.username}"> <jsp:forward page="Login.jsp" /> </c:if> </c:if> </c:forEach> </c:otherwise> </c:choose> |
下面的代码检查当 post 该页面时,参数 nodirectflights
是否被设为 true。如果继续查看该代码,那么可以发现,表单的动作是 post to the CheckFlightsServlet。根据用户选择的出发地和目的地,如果 CheckFlightsServlet 没有任何直达航班,则参数 nodirectflights
被设为 true,用户返回该页面,这个代码片段将显示关于没有直达航班的消息。
清单 5. 在 Welcome.jsp 中显示关于是否有直达航班的消息
<c:if test="${nodirectflights == 'true'}" > <p> There were no direct flights between <font color="blue" size="5"> ${cityNameFrom}</font> and <font color="blue" size="5"> ${cityNameTo}</font>. <br> Please select another flight. </p> </c:if> |
您可以使用 JSTL core out
标记来显示传递给 JSP 的会话对象或请求对象中的参数。登录成功之后,用户 ID 被放入 Session 对象,并且在用户访问 Welcome.jsp 页面时显示在该页面上。而且,注意用于包括 CalendarServlet 的 jsp:include
标记,CalendarServlet 用于显示当前的月、日和年,并且有一个用于选择出发日期的下拉框。
清单 6. 成功登录之后
<H3> Welcome to Derby Air, <c:out value="${username}" />!</H3> <p> Please proceed to select a flight. </p> <form action="CheckFlightsServlet" method="post"> <table width="50%"> <tr> <td valign="top"> <b>Departure Date:</b><br> <jsp:include page="/CalendarServlet"> <jsp:param name="type" value="orig" /> </jsp:include> </td> |
下面这段代码使用 JSTL SQL 库。在像下面这样使用 sql:query
标记之前,您已经在应用程序的 web.xml 文件中设置了 DataSource。以后将讨论那个条目,但是现在请注意这个标记使用起来有多么容易。代码中发出对 CITIES
表的查询,以返回 APP.CITIES
表的 city_name
、country
和 airport
列中所包含的值。查询的结果放在一个名为 cities
的变量中,这是一个 javax.servlet.jsp.jstl.sql.Result
对象。Result 对象有一个名为 getRows()
的方法,该方法返回对象中包含的所有行。这些行作为一个 java.util.SortedMap
对象数组返回。
清单 7. 使用 SQL 标记库
<sql:query var="cities"> SELECT CITY_NAME, COUNTRY, AIRPORT FROM APP.CITIES ORDER BY / CITY_NAME, COUNTRY </sql:query> |
下面展示了通过 forEach
标记对 cities
Result 对象中包含的行的迭代。在对这个数组的每一次迭代中,变量 city
包含一个 SortedMap 对象。Expression Language 允许通过引用表示数据库中一行的特定 SortedMap 对象中的列名,来访问每个行中的每个列。
清单 8. 输出 SQL 查询的结果
<td> <b>Origin:</b><br> <select name="from" size="4"> <c:forEach var="city" items="${cities.rows}"> <option value="${city.airport}"> ${city.city_name}, ${city.country}/ </option> </c:forEach> </select> <br><br> </td> </tr> |
这里不显示该页面的其他部分。这段代码像前面生成 Origin 一样输出 Destination 下拉框,然后提供一个按钮,以便用户提交查询来查看出发地(Origin)和目的地(Destination)之间的航班。
![]() ![]() |
![]()
|
在运行 LowFare Air 之前,如果 Derby Network Server 还没有运行,那么需要启动它。右键单击 LowFareAir 文件夹,然后选择 Apache Derby > Start Derby Network Server。
现在右键单击 Project Explorer 视图中的 Welcome.jsp 文件。选择 Run As > Run On Server。
图 11. 在 Tomcat Server 上运行 Welcome.jsp
![运行 Welcome.jsp](https://i-blog.csdnimg.cn/blog_migrate/c6ef996161f292b9f7650511348d2b63.png)
这样将弹出 Run on Server 向导。按照下面的步骤完成该向导:
- 选择 localhost 作为 Server 的主机名。对于服务器类型,展开 Apache 文件夹并选择 Tomcat v5.0。 选中 Set server as project default 复选框。单击 Next 按钮。
- 在 Add and Remove Projects 窗口中,确信 LowFareAir 项目列出在 Configured Projects 区域中。如果 LowFareAir 项目没有出现在那里,而是出现在 Available Projects 类别中,那么将它转移到 Configured Projects 类别中。单击 Finish。
这将启动外部的 Tomcat 服务器,并打开一个浏览器窗口,以便在这个窗口运行 JSP。在 Windows 中,默认情况是在 Eclipse 中打开一个内部浏览器。而在 Linux 中,默认情况是打开外部浏览器。
为了配置外部浏览器的启动:
- 选择 Window > Preferences。
- 选择 General 树项,然后选择 Web Browser。
- 选择 Use external Web browser 按钮,然后从列表中列出的可用浏览器中选择一个。
- 单击 OK 设置首选项。
用不同的浏览器检查 Web 页面总是一个很好的习惯。不同的浏览器在呈现一些 HTML 元素以及处理 cookie 的默认方式上会有一些差异。
如前所述,第一次打开 Welcome.jsp 时,会转入 Register.jsp 页面。 由于还没有设置 derbyCookie,所以 Welcome.jsp 会将您带到 Register.jsp,以便创建一个用户 ID 和密码。见图 12。
图 12. 带新用户 ID 条目的 Register.jsp
![Register.jsp](https://i-blog.csdnimg.cn/blog_migrate/828e17f3f3611659abceb433e6dba8c3.png)
当您输入一个用户 ID 和密码,并单击 Register New User 按钮时,这些值被传递给 LoginServlet 类。现在打开这个 Java 类,这个类位于 LowFareAir > Java Resources > JavaSource > com.ibm.sample 文件夹和包结构下。
doPost 方法首先解析传入的参数,包括您刚才在 Register.jsp 中设置的用户 ID 和密码。
清单 9. LoginServlet 类的 doPost 方法
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { String user = request.getParameter("username"); String password = request.getParameter("password"); // Register.jsp set the parameter newuser String newUser = request.getParameter("newuser"); String loggedOut = request.getParameter("loggedOut"); |
然后,它通过调用 DerbyDatabase 类的 getConnInstance()
方法连接到 Derby 数据库。getConnInstance
方法返回一个到数据库的单态 java.sql.Connection
。
清单 10. 将 conn 变量设置为 DerbyDatabase 类的单态 Connection 对象
Connection conn = DerbyDatabase.getConnInstance(); |
下面一段代码确定用户是否为新用户,如果用户 ID 已存在,那么从数据库中选择用户 ID,否则,将用户 ID 添加到数据库。
清单 11. 在 LoginServlet 类中处理新用户
// the user is not new, so look up the username and password // in the APP.USERS table if (newUser == null || newUser.equals("")) { sql = "select * from APP.USERS where username = '" + user + "' and password = '" + password + "'"; String[] loginResults = DerbyDatabase.runQuery(conn, sql); // if the query was successful one row should be returned if (loginResults.length == 1) { validUser = true; } } // the user is new, insert the username and password into // the APP.USERS table else { sql = "insert into APP.USERS (username, password) values " + "('" + user + "', '" + password + "')"; int numRows = DerbyDatabase.executeUpdate(conn, sql); if (numRows == 1) { validUser = true; } } |
为验证用户 ID Susan 是否被添加到 APP.USERS 表中,打开 Derby 插件中的 SQL 工具 ij
,查询 APP.USERS 表。
为了打开 ij
,右键单击 LowFareAir 文件夹,然后选择 Apache Derby > ij (Interactive SQL)。 从 ij
中发出 connect 语句连接到 airlinesDB
数据库,并运行查询 select * from APP.USERS;
,看看您输入到浏览器中的用户 ID 是否出现在这里。在这个例子中,用户 ID 是 Susan。
注意:对于在控制台视图中光标的位置,3.1 版的 Eclipse 与之前的版本相比有些不同。光标总是停留在一行的开始处。虽然看上去有些古怪,但是如果您开始在 ij 提示符下输入内容,光标又会回到适当的位置,也就是在 ij 中的 'j' 之后。
清单 12. 连接到 airlinesDB 数据库
connect 'jdbc:derby://localhost:1527/airlinesDB'; select * from APP.USERS; |
ij
的输出如下所示。
图 13. 来自 APP.USERS 表的 ij 结果
![APP.USERS 表结果](https://i-blog.csdnimg.cn/blog_migrate/31941e805d020bded89169156ff95ba2.png)
Register.jsp 正确地传递这些值,而 LoginServlet.java 则将用户 ID 和密码正确地插入到表中。这样,用户 ID 'slc' 和密码 'slc' 便已经在表中。
LoginServlet.java 中的其他代码处理不正确的用户 ID 和密码,然后,如果一切没问题,则将结果送到 Welcome.jsp。下图展示了 Origin 为 Albuquerque、Destination 为 Los Angeles 时的 Welcome.jsp。注意,用户 ID 被从 LoginServlet.java 传递到 Welcome.jsp,以便显示。
图 14. 成功登录之后的 Welcome.jsp
![成功登录之后的 Welcome.jsp](https://i-blog.csdnimg.cn/blog_migrate/707596e990d495144a79f3ee804b4aaa.png)
Welcome.jsp post 到 CheckFlightsServlet.java。打开 CheckFlightsServlet.java。关于这个 servlet 要注意的一点是,在解析传入的参数之后,它调用 DerbyDatabase
方法 origDestFlightList()
。这个方法返回一个 FlightsBean
对象数组。
清单 13. CheckFlightsServlet 类
Connection conn = DerbyDatabase.getConnInstance(); FlightsBean[] fromToFlights = / DerbyDatabase.origDestFlightList(conn, from, to); |
当 FlightsBean
数组填充了内容之后,CheckFlightsServlet
将结果放入变量名为 fromToFlights
的会话对象。
清单 14. 将 FlightsBean 数组放入会话对象
request.getSession().setAttribute("fromToFlights", fromToFlights); |
现在打开 DerbyDatabase.java 类,看看这个方法做些什么。为便于查看,其中部分代码的格式稍微作了调整。
清单 15. 查看 DerbyDatabase 类中的 origDestFlightList 方法
public static FlightsBean[] origDestFlightList(Connection conn, / String origAirport, String destAirport) { String query = "select flight_id, segment_number, orig_airport, " + "depart_time, dest_airport, arrive_time, meal, flying_time, miles," + "aircraft from app.flights where ORIG_AIRPORT = ? AND " + "DEST_AIRPORT = ?"; List list = Collections.synchronizedList(new ArrayList(10)); try { PreparedStatement prepStmt = conn.prepareStatement(query); prepStmt.setString(1, origAirport); prepStmt.setString(2, destAirport); ResultSet results = prepStmt.executeQuery(); while(results.next()) { String flightId = results.getString(1); String segmentNumber = results.getString(2); String startAirport = results.getString(3); String departTime = results.getString(4); String endAirport = results.getString(5); String arriveTime = results.getString(6); String meal = results.getString(7); String flyingTime = String.valueOf(results.getDouble(8)); String miles = String.valueOf(results.getInt(9)); String aircraft = results.getString(10); list.add(new FlightsBean(flightId, segmentNumber, startAirport, departTime, endAirport, arriveTime, meal, flyingTime, miles, aircraft)); } results.close(); prepStmt.close(); } catch (SQLException sqlExcept) { sqlExcept.printStackTrace(); } return (FlightsBean[])list.toArray(new FlightsBean[list.size()]); } |
origDestFlightList
方法使用 PreparedStatement 发出一个 SQL 查询,然后将结果放入一个 FlightsBean[]
数组。下面显示了 FlightsBean
的一个构造函数。
清单 16. FlightsBean 的一个构造函数
public FlightsBean(String flight_id, String segNumber, String origAirport, String depart_time, String destAirport, String arrive_time, String food, String flying_time, String mile, String jet) { flightId = flight_id; segmentNumber = segNumber; startAirport = origAirport; departTime = depart_time; endAirport = destAirport; arriveTime = arrive_time; meal = food; flyingTime = flying_time; miles = mile; aircraft = jet; } |
当 origDestFlightList
方法填充好 FlightsBean
数组后,CheckFlightsServlet servlet 继续进行处理,结果被传到 GetFlights.jsp 页面。
在下一节中,您将使用 WTP 的 JSP 调试器来查看当选择一个航班时 FlightsBean
中返回的值。
下一节将以 debug 模式启动 Tomcat 服务器,所以这里先停止 Tomcat 服务器。为此,选择工作区右下角的 Servers view 选项卡。然后在 Tomcat Server 行单击右键并选择 Stop。
图 15. 在 WTP Servers 视图中停止 Tomcat 服务器
![停止 Tomcat](https://i-blog.csdnimg.cn/blog_migrate/24cc4265bbcb5471d32ac4bb7015450d.png)
![]() ![]() |
![]()
|
对于代码的研究先告一段落,这里总结一下您通过探索和配置示例应用程序所看到的东西:
- WTP
- 通过 Database Explorer 视图配置到使用 Derby Client 驱动程序的 Derby 10.1 数据库的连接。
- 从 Database Explorer 视图抽取 FLIGHTS 表中的内容。
- 在 Database Explorer 视图中,使用 Data > Open 菜单项插入一行到 FLIGHTS 表。
- 从一个 JSP 文件上使用 Run As > Run On Server 选项启动 Tomcat 服务器。
- 在 JSP 编辑器中打开和查看 JSP。
- 使用 Servers 视图停止 Tomcat 服务器。
- Derby 插件
- 添加 Apache Derby 特性到动态 Web 项目中。
- 使用 Project Properties 菜单配置 Derby 系统属性。
- 通过 ij 运行整个 SQL 脚本。
- 通过 ij 发出 SQL 命令。
- 启动和停止 Derby Network Server。
现在让我们来看 WTP 的 JSP 调试功能。
现在,在 Derby airlinesDB APP.USERS
表中至少有一个有效的用户,您可能还添加了其他用户。在运行整个应用程序之前,先在 GetFlights.jsp 页面中设置一个断点,然后以 debug 模式启动 Tomcat 服务器。
为设置断点,打开 GetFlights.jsp,在以 <c:set var="myradiobutton"
开始的那行代码左边的灰色区域单击右键。选择 Toggle Breakpoints,如下所示。
图 16. 在 GetFlights.jsp 中设置断点
![设置一个断点](https://i-blog.csdnimg.cn/blog_migrate/106589bc330c01b68137de16e45911cf.png)
这个断点在左边的灰色区域看上去像一个蓝点。现在从 Project Explorer 中(确保 Derby Network Server 仍在运行),右键单击 Welcome.jsp 并选择 Debug As > Debug On Server。Tomcat Server 现在将以 Debug 模式启动,并进入 Welcome.jsp 页面,该页面提示输入用户 ID 和密码。
输入您之前输入过的用户 ID 和密码,或输入 slc
作为用户 ID,slc
作为密码。如果您没有删除已经设置好的 cookie,那么您不必再次登录,就可以在 Welcome.jsp 中选择航班。Origin to Destination 中列出的航班并不都是直达的。选择 Albuquerque 作为 Origin,选择 Los Angeles 作为 Destination,因为这个航班是直达的。然后单击 Submit Query。
这时,Eclipse 应该提示您切换到 Debug 透视图。确认切换透视图。当出现 debug 透视图时,在工作区的右上角将出现 Variables 视图。在左下角,还将出现 GetFlights.jsp 编辑器视图,这个视图表明您设置断点的位置。
Variables 视图可能不会立即有值出现。您可能需要进入 Debug 视图,并选择已经被挂起的线程。如下所示,当您在 Debug 视图中展开挂起的线程,并选择 GetFlights.jsp 时,Variables 视图中将出现值。
在 Variables 视图中,查找您的 core JSTL when
标记。展开树,找到 _jspx_th_c_when_0=WhenTag
项。见图 17。
图 17. 从 JSP Debug 透视图中查看变量
![查看变量](https://i-blog.csdnimg.cn/blog_migrate/e7d48263f2391eaca27c5770fc708e67.png)
注意 WhenTag
中对父标记 ChooseTag
的引用。展开父标记 ChooseTag
,一起的还有父标记 ForEachTag
。展开 ForEachTag
,最后展开等于 FlightsBean
的变量。如果您成功地执行了这一系列动作,那么 Variables 视图看上去应该如下所示。
图 18. Debug 模式下的 FlightsBean 值
![Debug 模式下的 FlightsBean 值](https://i-blog.csdnimg.cn/blog_migrate/2c947e01cfebf06ac5948d6209cb9a77.png)
这个视图显示 FlightsBean 对象中的值,这是在选择启程机场为 Albuquerque,目的机场为 Los Angeles 的情况下得到的。当为 Web 应用程序排除故障,特别是像这里那样查看变量时,JSP 调试器极为有用。
现在单击左上角菜单项上的 Resume 按钮(看上去像一个绿色的箭头),以跳过断点。浏览器将显示 GetFlights.jsp 页面的输出。在浏览器中,选择可用的航班(航班 AA1111),并单击 Book Flight 按钮。
接下来的页面给您最后一次机会预订当前航班或者查看其他航班。单击 Book Flight 按钮继续。 接下来的页面将如下所示。
图 19. Flight History
![Flight History Browser 视图](https://i-blog.csdnimg.cn/blog_migrate/e4b27459e22c014a0ca03c96dfc71f8c.png)
当您在前一个屏幕上单击 Book Flight 时,将有一行被插入到 APP.FLIGHTHISTORY 表中。由于您已经知道如何使用 ij 和 Database Explorer,您可以验证这一行是否真的插入到了表中。
至此,用户可以返回并选择一个新的航班,或者退出应用程序。
![]() ![]() |
![]()
|
在安装和配置 WTP 平台的过程中,您使用了外部的 Tomcat 服务¡器,调试了一个 JSP 文件,使用 Database Explorer 配置了到 10.1 Derby 数据库的一个连接,并使用了 Database Explorer 来浏览一个表以及插入一行。
您学习了 Derby 插件的用法,包括添加 Apache Derby 特性,启动和停止 Network Server,使用 ij 运行 SQL 脚本和发出即席 SQL,以及设置 derby.system.home
属性。
您配置了 Web 应用程序的 web.xml 文件,以便使用 Derby 作为数据源。
最后,您使用 JSTL SQL 标记库对被配置为数据源的 Derby 数据库发出查询。
本文有望为使用 WTP 和 Derby 插件中的多种工具提供一个坚实的基础。以这些基础为起点,您可以开发健壮的使用 Derby 作为数据源的 Web 应用程序。
![]() ![]() |
![]()
|
描述 | 名字 | 大小 | 下载方法 |
---|---|---|---|
Derby Database files for the Web Application | LowFareAirData.zip | 216 KB | FTP![]() ![]() |
LowFare Air war file | LowFareAir.war | 31 KB | FTP![]() ![]() |
![]() | ||||
![]() | 关于下载方法的信息 |
转自:http://www.ibm.com/developerworks/cn/db2/library/techarticles/dm-0509cline/#download