原文:开发基于JBoss AS 7.2.0的Java EE程序 - 03.如何创建EJB、WAR、Connector和EAR工程
概述
本文描述如何创建基于JBoss AS 7.2的Java EE程序的EJB、WAR、Connector和EAR工程。
1. 创建 Enterprise Application Project
1.1 在Eclipse中先创建一个Server
点击上图的“Finish”按钮,一个JBoss AS Server就创建好了。
启动日志:
现在我们停止JBoss AS 7.2
1.2 创建 Enterprise Application Project
依次导航菜单: "File" > "New" > "Project ..." ,在弹出来的界面中,选择 "Java EE > Enterprise Application Project",如下:
点击上图中的“Next”按钮。
点击上图中的“Next”按钮。
注意选中“Generate application deployment descriptor”勾选框:
点击上图中的“New Module...”按钮。
我们修改自动生成的modules名字:
点击上图中的“Finish”按钮。
结果:
设置文本编辑器的编码格式:
现在我们把application.xml中的 <context-root>ybxiang-forum-war</context-root> 改成 <context-root>/</context-root>
2. 为ybxiang-forum-war 添加基本功能
2.1 添加JSF功能
结果:
(a) web.xml内容:
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" version="3.0">
<display-name>ybxiang-forum-war</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>/faces/*</url-pattern>
</servlet-mapping>
</web-app>
(b) faces-config.xml内容:
<?xml version="1.0" encoding="UTF-8"?><faces-config
xmlns="http://java.sun.com/xml/ns/javaee"
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_1.xsd"
version="2.1"></faces-config>
我们为web.xml删除 <display-name>元素,并添加一些内容,如下:
<?xml version="1.0" encoding="UTF-8"?>
<web-app version="3.0" xmlns="http://java.sun.com/xml/ns/javaee" 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-app_3_0.xsd">
<context-param>
<param-name>PARAMETER_ENCODING</param-name>
<param-value>UTF-8</param-value>
</context-param>
<context-param>
<param-name>javax.faces.PROJECT_STAGE</param-name>
<param-value>Development</param-value>
</context-param>
<context-param>
<param-name>javax.faces.STATE_SAVING_METHOD</param-name>
<!-- do NOT use 'server' value, because it will cause javax.faces.application.ViewExpiredException -->
<param-value>client</param-value>
</context-param>
<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>/faces/*</url-pattern>
</servlet-mapping>
<session-config>
<session-timeout>600</session-timeout>
</session-config>
<welcome-file-list>
<welcome-file>faces/index.xhtml</welcome-file>
</welcome-file-list>
</web-app>
其中:
- PARAMETER_ENCODING:设置 表单(form)提交内容的编码格式。
- javax.faces.STATE_SAVING_METHOD:用于将session状态信息存储在客户端,如果使用'server',那么客户端可能出现异常:javax.faces.application.ViewExpiredException
- session-timeout:设置会话超时时间,单位是分钟。
- welcome-file-list:设置欢迎页
2.2 模板
(a) template/template.xhtml
<?xml version='1.0' encoding='UTF-8' ?>
<!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">
<h:head>
<title>
<ui:insert name="title"/>
<h:outputText value=" - www.javaarm.com" />
</title>
<link rel="shortcut icon" href="#{request.contextPath}/img/favicon.ico"/>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<link rel="stylesheet" type="text/css" media="all" href="#{request.contextPath}/css/template.css" />
<ui:insert name="headMetaData"/>
</h:head>
<!-- make the whole body in center -->
<style type="text/css">
<!--
body{ margin:0 auto;}
-->
</style>
<h:body style="width:1000px;" styleClass="yui-skin-sam" >
<a name="header" id="header" />
<ui:include src="/template/navigator.xhtml" />
<hr class="separator" />
<f:view>
<h:messages id="messages" globalOnly="true" styleClass="message"
errorClass="errormsg" infoClass="infomsg" warnClass="warnmsg"
rendered="#{showGlobalMessages != 'false'}"/>
<ui:insert name="body" />
</f:view>
<hr class="separator" />
<a name="footer" id="footer" />
<h:outputLink value="#{request.contextPath}/faces/index.xhtml" ><h:outputText value="Home" /></h:outputLink>
<h:outputText value=" " />
<h:outputLink rendered="#{not forPrint}" value="#header"><h:outputText value="Header" /></h:outputLink>
<hr class="separator" />
<ui:include src="/template/footer.xhtml" />
</h:body>
</html>
(b) template/navigator.xhtml
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<ui:composition xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:h="http://java.sun.com/jsf/html">
<div>
<h:form id="search" >
<table width="100%" border="0" cellpadding="0" cellspacing="0" >
<tr>
<td width="50%">
<h:outputLink value="#{request.contextPath}/faces/index.xhtml" >
<h:outputText value="Home" />
</h:outputLink>
</td>
<td width="50%" style="text-align: right;" >
</td>
</tr>
<tr>
<td colspan="100">
<h:graphicImage value="#{request.contextPath}/img/biggrin.gif" style="border:0px;" />
<h:outputText value=" " />
</td>
</tr>
</table>
</h:form>
</div>
</ui:composition>
(c) template/footer.xhtml
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<ui:composition 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">
<div style="margin-top: 2px; text-align: center">
<h:outputText value="www.jdetail.com" />
</div>
</ui:composition>
(d) css/template.css
.separator{
border:0px; border-top: 1px dashed #6293bb;
}
.topic_separator{
text-decoration: none;background: #ffffff
}
.linelessLink{
text-decoration: none;
}
.message li {
background: no-repeat left center;
padding-top: 1px;
padding-left: 20px;
margin-left: 3px;
}
.message li.infomsg {
background-image: url(../img/msginfo.png);
}
.message li.errormsg {
background-image: url(../img/msgerror.png);
}
.message li.warnmsg {
background-image: url(../img/msgwarn.png);
}
(e)index.xhtml
<!DOCTYPE composition PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<ui:composition xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
template="/template/template.xhtml">
<ui:define name="title">
<h:outputText value="JAVA and ARM research" />
</ui:define>
<ui:define name="headMetaData">
<!-- 'head' module is used to include css/script files, do NOT display anything in it. -->
<link rel="stylesheet" type="text/css" media="all" href="#{request.contextPath}/css/index.css" />
</ui:define>
<ui:define name="body">
<div>
<div class="div-domain"><h:outputText value="Administration" /></div>
</div>
</ui:define>
</ui:composition>
2.4 测试
效果图:
3. ybxiang-forum-ejb 添加基本功能
3.1 添加JPA功能
现在我们把 persistence.xml 修改如下:
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.1"
xmlns="http://java.sun.com/xml/ns/persistence"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_1.xsd">
<persistence-unit name="ybxiang-forum-persistence-unit">
<jta-data-source>java:jboss/datasources/ybxiangForumMySqlDataSource</jta-data-source>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5Dialect"/>
<property name="hibernate.hbm2ddl.auto" value="update"/>
<property name="hibernate.show_sql" value="false"/>
<property name="hibernate.format_sql" value="true"/>
</properties>
</persistence-unit>
</persistence>
3.2 数据源配置
参见:开发基于JBoss AS 7.2.0的Java EE程序 - 02.如何配置MySql数据源
3.3 测试
重启 JBoss AS 7.2,相关日志如下:
16:07:21,093 INFO [org.jboss.as.connector.subsystems.datasources] (MSC service thread 1-6) JBAS010400: Bound data source [java:jboss/datasources/ybxiangForumMySqlDataSource]
...
16:07:23,078 INFO [org.hibernate.Version] (ServerService Thread Pool -- 58) HHH000412: Hibernate Core {4.2.0.CR1}
16:07:23,109 INFO [org.hibernate.cfg.Environment] (ServerService Thread Pool -- 58) HHH000206: hibernate.properties not found
16:07:23,109 INFO [org.hibernate.cfg.Environment] (ServerService Thread Pool -- 58) HHH000021: Bytecode provider name : javassist
16:07:23,453 INFO [org.hibernate.ejb.Ejb3Configuration] (ServerService Thread Pool -- 58) HHH000204: Processing PersistenceUnitInfo [
name: ybxiang-forum-persistence-unit
...]
蓝色的日志意味着我们在persistence.xml中的配置已经生效。
4. classpath 配置
4.1 EJB项目的classpath
- 我们在ejb项目中,通常要用到javax.persistence.*,因此,我们需要把JPA的API jar包添加到ejb项目的classpath中。
- 同理,j2ee程序,通常需要开发EJB的,所以ejb对应的jar包也需要包含到ejb项目的classpath中。
- 如 果我们想要使用JBoss logging,那么我们还需要引入jboss logging的jar包。当然,我们也可以使用JDK logging,我们强烈推荐使用JDK logging。JBoss log系统会正确把日志打印到 server.log 中的,参见 JBoss7.1.1 > article > JBoss Logging。
- 我 们通常会把密码以hash的方式存储到数据库。因此,还需要jboss的picket box对应的jar包。org.jboss.crypto.CryptoUtil和org.jboss.security.auth.spi.Util, 都可以用于对密码计算Hash!
注意:所有这些jar包,都可以在$JBOSS_HOME/modules/system/layers/base下面的那些子目录中找到。
现在,我们的EJB项目的classpath如下:
4.2 WAR 项目的classpath
- 基于JSF的WAR项目中,通常要用到JSF API包。
- WAR项目,通常会用到servlet API,所以这个包也得加上。
- 我们通常会把EJB通过注解“@EJB”注入到JSF的MBean中,用于读写数据,所以,EJB对应的API包也要加入。
现在,我们的war项目的classpath如下:
5 网站规划
我们要为本网站实现下列功能:
- 用户注册、电子邮件激活账号、基于JAAS登陆、电子邮件找回密码、控制台设置个人信息。
- 分页显示文章
- 文件上传
Comments