代码改变世界

使用myeclipse集成struts,hibernate,spring的一个示例程序

2007-10-11 10:29  Jacky_Xu  阅读(713)  评论(0编辑  收藏  举报
在java企业应用领域,ejb的功能强大同ejb的配置复杂,难于学习一样出名。但在以前我们又有什么办法呢?只有硬着头皮来学ejb。真有点“明知山有虎,偏向虎山行”的精神。现在形式有了乐观的变化,java开源的持续走红,使得开发java企业级应用不再局限于ejb领域。这里我主要介绍一下怎样采用开源的Spring,Hibernate以及Struts构建一个轻量级的架构。MyPlaces(自我空间 自由展现)(Y2P5W N O u G#V
一、整体架构介绍MyPlaces(自我空间 自由展现) l0C%y.W0_ q x#d
软件工程领域,为了降低模块耦合度,提高模块的可重用性,分层一直是广为采纳的一个方法。其实分层还可以使开发人员专注于某一层进行开发,使得软件开发的分工变细,提高生产效率(这一点上堪比福特发明的流水线生产汽车的做法,各个工人负责特定部件的生产,最后组装)。MyPlaces(自我空间 自由展现)(s#q d { @,f-Q R
一个企业级的java应用,通常分为以下几层:UI层,业务逻辑层,数据持久层,域对象层。下面对这几层分别作简要介绍:MyPlaces(自我空间 自由展现)'W(V @7Y0R B1x'F
1.      UI层:负责与用户交互,包括:接受用户的请求,把处理结果返回给用户。这里我们采用struts来UI层,虽然比起Tapestry以及JSF这些事件驱动的表现层技术而言,Struts的设计显得有些老土,但它目前仍是表现层事实上的标准,所以我们还是选用它。
P cC#~ r D @Guest2.      业务逻辑层:主要负责具体的业务处理。通过Spring的IOC以及AOP实现各个功能的耦合相连
$A q S o P g#LGuest3.      数据持久层:主要负责与底层的数据库打交道。这里我们采用Spring封装的Hibernate操作来简化实际的编码。主要的操作为CRUD(create ,read,update,delete)
r5e7r S!B;c h+OGuest4.      域对象层:具体的实体类,如老师,学生等等这些具体的类(注意:需要与数据库中的某一标对应)。MyPlaces(自我空间 自由展现)4e L z f9b%E _%v
以上只是简单介绍了各个层的划分以及各层所对应的开源框架,要详细了解各层的具层信息,需要访问 struts,hibernate,spring的官方网站。
^$W q!f ~ uGuest二、实例分析MyPlaces(自我空间 自由展现)8X1i X l C8] t W
实例说明:一个网站登录的例子,比较简单,但能说明各层是如何协调工作的。
T T'W b ~!l @5A } zGuest工具:jdk1.5,eclipse3.2,myeclipse5.0GA,mysql5.0,tomcat5.5,至于这几个工具到底该怎么装这里我就不多说了,大家不清楚的可以到网上搜搜。下面是具体操作步骤:MyPlaces(自我空间 自由展现)"L5l S o'L l G%[,X
预备工作:用mysql创建一个test数据库,再创建一个user表,再创建两个字段username和password。脚本如下MyPlaces(自我空间 自由展现)/u ? K i O a
MyPlaces(自我空间 自由展现) R C f p1P x
DROP DATABASE IF EXISTS `test`;
([+Q M E E1u9}$C NGuestCREATE DATABASE `test`
W } U/F2R u5Q5N },V FHGuestUSE `test`;MyPlaces(自我空间 自由展现) H ?,p's _1D H } ] w1A
MyPlaces(自我空间 自由展现)(h | i e*s$~ s y u
CREATE TABLE `user` (MyPlaces(自我空间 自由展现)$N v ^ Jb*b
`id` int(11) NOT NULL auto_increment,MyPlaces(自我空间 自由展现) A z ? s i x c v9t#J ]
`username` varchar(30) NOT NULL default '',MyPlaces(自我空间 自由展现) e:c F!u Y-`;w ` |+A
`password` varchar(30) default '',MyPlaces(自我空间 自由展现) Z y5f+c+[J
PRIMARY KEY (`id`)MyPlaces(自我空间 自由展现) F*B)n1o&@$j5[ U'p"T
) ENGINE=InnoDB DEFAULT CHARSET=gb2312;
'?'[ o'U A"E Z NGuest打开myeclipse的database explore透视图MyPlaces(自我空间 自由展现)*V Y X _ i)F J0d
MyPlaces(自我空间 自由展现)4s M:Z j E m
MyPlaces(自我空间 自由展现) m ~"i M'| R v x H7c q r

S ^ [ ] E O8]GuestMyPlaces(自我空间 自由展现) f5n r#K Y8a R
右键单击左侧的空白区域 ,点击 new 按钮MyPlaces(自我空间 自由展现) {+}9H2E9R/a r b z
MyPlaces(自我空间 自由展现)(i E ~!W p N e6S {

_!z t$e W4GGuestMyPlaces(自我空间 自由展现) s e1x6mk x \
单击“configure database driver”来配置数据库的驱动,你必须有mysql的jdbc驱动 ,没有的到mysql的官方网站上下载MyPlaces(自我空间 自由展现) c ^ S+X h K

z3C$x ? })[ f5b aGuestMyPlaces(自我空间 自由展现)%E G G.v.W/v2r
MyPlaces(自我空间 自由展现) S$c"M T o L$m M p4o
测试数据库配置是否成功。MyPlaces(自我空间 自由展现) p `$Q Y p&u R$K l
MyPlaces(自我空间 自由展现),x L y Q4O%O-@ m%G:}
MyPlaces(自我空间 自由展现) J/M,S'F,p L T5z

$L(] O R&n6F L,w"x UGuest
8d#\3z K c.iGuest1.      新建一个myeclipse的web工程MyPlaces(自我空间 自由展现)7J1l8T3Z n v x
MyPlaces(自我空间 自由展现)*R7I n Z V

E(g3l B)y S!N z-yGuestMyPlaces(自我空间 自由展现) a"k u | X
MyPlaces(自我空间 自由展现) ? S c D;n
2.      引入Spring包
H9A v0@ ^:U G9g q P g/rGuest右键工程名MyPlaces(自我空间 自由展现) J*Y&z!Q5U k%?
MyPlaces(自我空间 自由展现)'r l } b F i"\3d
MyPlaces(自我空间 自由展现)6Q g(D C f f \/T `

)O a H P8i x V5{0` PGuestMyPlaces(自我空间 自由展现) b$s#C Q u { b6S I

U r#T'S W$aGuestMyPlaces(自我空间 自由展现)-j ]"A4B0M
MyPlaces(自我空间 自由展现) j D.[8K$~
注意:这里为了省得以后再添加spring的相关包,所以一次性的选中了所有的包。选中MyPlaces(自我空间 自由展现)5S0m-x*h(| q)C S
Copy选项,它会把这些包拷贝到/WebRoot/WEB-INF/lib目录下,方便以后的实际部署。
.G)H R6X2D)\*^ F GGuest3.      添加hibernate包MyPlaces(自我空间 自由展现) o @0X9r U {5F w i
MyPlaces(自我空间 自由展现)$[ M x u3V `$}$s

{ e @ C#N/v1zGuestMyPlaces(自我空间 自由展现) p&F i j(u j'q/q
系统会检测到该工程已经添加了Spring包,选择使用Spring的配置文件MyPlaces(自我空间 自由展现)4p } O T-X h b2?
MyPlaces(自我空间 自由展现)*e;n v(} P w0Yu

8F6o,Z x L+V X7?Guest
+fK N7q X(j @Guest点击 next
W%s ` [ l e w$u r8i G:R IGuestMyPlaces(自我空间 自由展现) N:| @ [ ^ i4Z
MyPlaces(自我空间 自由展现)/~4b2J;S6M"E _ f H
MyPlaces(自我空间 自由展现) kK&g }*C W M(} d8?
点击 next
+H g'u&?7p$^8MGuestMyPlaces(自我空间 自由展现) f f8e V&T r!y
MyPlaces(自我空间 自由展现)6o1q s0R J$y T"W#R

H D g%L3c;[ `Guest点击 next
8B4k \8j&y u z#zGuest
M r"l [)m%^5~ MGuest
C d ?-R S w I FGuestMyPlaces(自我空间 自由展现) @3z v h1U x e
最后点击Finish按钮即可。
H I'd+q kGuest4切换到database explore视图,右键 点击 user 表的“Hibrnate Reverse Engineering”
r$a4Z d k(t4tGuestMyPlaces(自我空间 自由展现)%Q A ~ ` g'N V)D
MyPlaces(自我空间 自由展现) { E f9\#@8l8V
MyPlaces(自我空间 自由展现) Y N-L ] ` ] m:X)O
弹出如下窗口MyPlaces(自我空间 自由展现);e c0q.@ S x4K

L } U.E e,xGuest
D H g X2q4o X+ZGuestMyPlaces(自我空间 自由展现) N P:~ k m n.A U;V
点击 “next”
&F6_8j1v b EGuest
2L _ b$W;L|3Y J [ S,`;F ZGuestMyPlaces(自我空间 自由展现)6K P#T&P9N

h:r m D W A zRGuest再单击finish
0G b J5Z'x/@5F!Z$g HGuest     在包视图中 可以看到 src下多了一个名为vo的package以及该包下的四个文件
%n8w']'z a E-T gGuest
'A t9Z U Q*bGuest
&R W p n7{ jGuest
V9c I r tGuest为了更加直观地显示分层,我另建了一个名为dao的package,并把UserDAO.java移到dao中
5Y,_5{ C z1p8h { hGuest
i+H `2^8] B-a-wGuestMyPlaces(自我空间 自由展现)0Q E o U'I8v;~
MyPlaces(自我空间 自由展现) F5I m7S [+C&w f
同时注意在applicationContext.xml中把对UserDAO的引用部分也作相应修改。
I3q f j6z"qGuest5.      建立业务逻辑层代码MyPlaces(自我空间 自由展现)-Q%{ q j M1l X:F Q
新建一个名为service的包,再在里面建立一个Service类,代码如下
3m L f/q G W { Q'VGuestpackage service;
c:`"D%z } p U |GuestMyPlaces(自我空间 自由展现).g(_z aU y9c!?
import java.util.List;MyPlaces(自我空间 自由展现)3@;c)s(Z V A%Q H%m f
MyPlaces(自我空间 自由展现);]*b%? c e H I4v
import vo.User;
}7b!q u {._ Z O0aGuestimport dao.UserDAO;
@ H q%u4c YGuest
&S I3u,X k;BGuestpublic class Service {
8J f j { w;k4u t6^ _'WGuest
k;e X-C'R#i QGuest     private UserDAO userDao;
r D Y [1NGuest
,t/h Q)e t w7M ^%aGuest     public UserDAO getUserDao() {
V b V G(C8K u+Z @.e2Y NGuest         return userDao;MyPlaces(自我空间 自由展现) Q M2Q ^+T
     }MyPlaces(自我空间 自由展现) F0~ d K Z _ f

,g7B T o e^,n vGuest     public void setUserDao(UserDAO userDao) {MyPlaces(自我空间 自由展现)&n z q%l4w W)S
         this.userDao = userDao;MyPlaces(自我空间 自由展现) K+yF*V!^'E(K C
     }
^ T)u+|+F l/Q/RGuest
*_3x6e q.z jGuest     public boolean isValid(User user) {//判断用户是否合法
{ q&j7d7d/Q,?GuestMyPlaces(自我空间 自由展现):x i0Jw.h6U%s { W _ H
         List result = userDao.findByExample(user);MyPlaces(自我空间 自由展现) E5z9T/H E z'^ z.L0d$X#[

&O:I _ l3R,BGuest         if (result.size() > 0)MyPlaces(自我空间 自由展现) N e @%M C k
               return true;
s,r'J @ xGuest         elseMyPlaces(自我空间 自由展现)6w*G/{7e k T
               return false;MyPlaces(自我空间 自由展现) x6N4G ^3n V
MyPlaces(自我空间 自由展现)'~,w N"m!O(g M p
     }
+_9e k U"l L!S { FGuest
p/h J Y b6I |Guest}
e;R2\ ? YGuest同时在applicationContext.xml中添加如下配置
p5i f*] T a H F IGuest<bean id="service" class="service.Service" singleton="false">MyPlaces(自我空间 自由展现)5K H S'p,m N,N
         <property name="userDao">MyPlaces(自我空间 自由展现) j&{$]!X A6ED
               <ref bean="userDao" />MyPlaces(自我空间 自由展现) h0P2j;p B s$} T g
         </property>
.? q/f t_!Z q)n w5|Guest     </bean>MyPlaces(自我空间 自由展现)3B,N.x3s%p%T f;l
6.配置UI层
3} { ^4H8J$m(|;o HGuest添加struts包,方法同添加spring一样
3U6h1G*P8Y e6_Guest
k D9z$G m m.w VGuestMyPlaces(自我空间 自由展现) |7w&l a)T6m }*e P0n

F H Z7l } z$| Q%F n CGuest配置struts-config.xml文件,在空白区域右键单击 new 一个 action ,actionForm ,jspMyPlaces(自我空间 自由展现) r-Z/[ ] j!P M

j2v L0D%]'p;X9V1} r)UGuestMyPlaces(自我空间 自由展现) f L-O.F c F V8` x
MyPlaces(自我空间 自由展现)6K1I+Z&@0A

Q e J7u H!m-d+v EGuestMyPlaces(自我空间 自由展现)$T&i C P D e l

9z"Y!h i A"A#K3T NGuestMyPlaces(自我空间 自由展现))f0] X w.S$V ^#`(J
MyPlaces(自我空间 自由展现) K*h @1i u n ?0i d V O

:H5~ }5[ Z c5?'F5^-VGuest
e7`2x c WGuest下一步MyPlaces(自我空间 自由展现)'i;q q(\-i { N1G f
对forward作设置,增加succeed转到welcome.jsp,fail转到login.jspMyPlaces(自我空间 自由展现) c t*R P'm+n V ^

P5c ?7S g5JGuest在WebRoot目录下建立一个welcome.jsp文件,显示用户登录成功后的欢迎信息。
o3} o r F XGuest6.      把struts和spring连接起来MyPlaces(自我空间 自由展现)8U6E%\ h s J^5? ~6E-v H
6.1修改struts-config.xml注意红色字体部分
T,V1H0| ~ I6H wGuest<action
M3@:q n uGuest     attribute="loginForm"MyPlaces(自我空间 自由展现) Q;~,X C;i P ] W
     input="/login.jsp"MyPlaces(自我空间 自由展现) | q G n6n(n6A$f.f'`
     name="loginForm"
Q _ x T-P EGuest     path="/login"MyPlaces(自我空间 自由展现)+? f _ E T
     scope="request"MyPlaces(自我空间 自由展现)-F U n*M1~+m @"A
     type="org.springframework.web.struts.DelegatingActionProxy">
_ D g1@ G+U CGuest     <forward name="fail" path="/login.jsp" />
9e.? K8s-}2mGuest     <forward name="succeed" path="/welcome.jsp" />MyPlaces(自我空间 自由展现):c%P7g ^ d*N!L6A x
</action>MyPlaces(自我空间 自由展现) p8` x O'K.G#v1{
MyPlaces(自我空间 自由展现) e \6K#y w&w
再在strut-config.xml中添加如下代码
L ~ B ` A;K3_Guest<plug-in className="org.springframework.web.struts.ContextLoaderPlugIn">MyPlaces(自我空间 自由展现) w w x/y t
<set-property property="contextConfigLocation" value="/WEB-INF/classes/applicationContext.xml" />MyPlaces(自我空间 自由展现))L h r p f s
</plug-in>>MyPlaces(自我空间 自由展现) E%u m:@8_$J G.c x
6.2修改applicationContext,增加以下内容MyPlaces(自我空间 自由展现) K } C#]!i S d pG H
<bean name="/login" class="web.action.LoginAction"
/h+R C2n ?8E0@ x ^9O iGuest         singleton="false">MyPlaces(自我空间 自由展现) T ~6@4y8} D&L
         <property name="service">
\8u"O Q pGuest               <ref bean="service" />
o Ee O ^ i mGuest         </property>MyPlaces(自我空间 自由展现) j r s*e%i ` K U9h k d
</bean>MyPlaces(自我空间 自由展现):X {"V S D/C R3D J K
6.3修改LoginAction.java部分代码,增加一个service变量,以及其 get/set方法(主要用于Spring IOC)。代码如下:
&x m9C!_'z.rGuest/*
n)o8e)B4e eGuest* Generated by MyEclipse StrutsMyPlaces(自我空间 自由展现) J J8c.n9v f"} K
* Template path: templates/java/JavaClass.vtl
9T1^ S'j(z J ~Guest*/
C a A G j5fGuestpackage web.action;
n*w(u u y&O E6JGuest
-i8\ q*u _Guestimport javax.servlet.http.HttpServletRequest;MyPlaces(自我空间 自由展现) R,W i)y ?
import javax.servlet.http.HttpServletResponse;
G X M'd E I X9P0CGuestimport org.apache.struts.action.Action;
1M ~'| `+x h,NGuestimport org.apache.struts.action.ActionForm;
M G ]2x mx.\8lGuestimport org.apache.struts.action.ActionForward;MyPlaces(自我空间 自由展现) F"` q1X d$L%Q
import org.apache.struts.action.ActionMapping;
c$w | b*~ M1dGuestimport web.form.LoginForm;MyPlaces(自我空间 自由展现)!q c/c R9Z
import service.Service;MyPlaces(自我空间 自由展现) k H e(H'A7l d
import vo.User;MyPlaces(自我空间 自由展现) Q+n'u q7B._ J;y

| ~&c i Z r v EGuest/**
&O c v B V DGuest* MyEclipse Struts Creation date: 09-27-2006
4p#Y v R F m G%E!^ iGuest* MyPlaces(自我空间 自由展现)/h0H k/?b
* XDoclet definition:MyPlaces(自我空间 自由展现) d u*p-g Y {&Z
* MyPlaces(自我空间 自由展现)3A {,f4Z w*? H N"T
* @struts.action path="/login" name="loginForm" input="/login.jsp"MyPlaces(自我空间 自由展现) V.Q O B w1m ?
*            scope="request" validate="true"
S4M7o-N Y dGuest* @struts.action-forward name="fail" path="/login.jsp"MyPlaces(自我空间 自由展现)2O4Z&f!l j.i Q0z5{/B
* @struts.action-forward name="succeed" path="/welcome.jsp"MyPlaces(自我空间 自由展现) p K-I7D'U6p&u6k Z v |
*/
f2F _ K N$\Guestpublic class LoginAction extends Action {
:U v I T C"~ E L {Guest     /*MyPlaces(自我空间 自由展现)0b |$Pp7a8i!S5H9g I
     * Generated MethodsMyPlaces(自我空间 自由展现)9p,{)^ H5i-^ ^2K;C k3l
     */
[(X [ v v;h s M {Guest
&D {1z Y F N t WGuest     /**MyPlaces(自我空间 自由展现)3U%{ ?-g \ X6b3L
     * Method executeMyPlaces(自我空间 自由展现) }$Z'L#T l N M
     *
z d y k f y v,cGuest     * @param mappingMyPlaces(自我空间 自由展现)(y(?0b R V5m ` p H1J
     * @param formMyPlaces(自我空间 自由展现) b7q,B$A.G G a
     * @param request
:T K n!o y3N } pGuest     * @param response
P { Y }7_:jGuest     * @return ActionForwardMyPlaces(自我空间 自由展现)4{ e(s i8~
     */MyPlaces(自我空间 自由展现) U8d W:G(d4n { [

|2K6}8m*\)C5F z-CGuest     private Service service;
em a*M e3s ]GuestMyPlaces(自我空间 自由展现)4U V5B!~ m!}
     public void setService(Service service) {MyPlaces(自我空间 自由展现) l k.e o \
         this.service = service;MyPlaces(自我空间 自由展现) z4a W p:K E
     }
| E q%] G8w4M[/yGuestMyPlaces(自我空间 自由展现) U @ L s T N
     public Service getService() {MyPlaces(自我空间 自由展现) u4[-@ r.g W:ai"p q
         return service;MyPlaces(自我空间 自由展现)&f1N!@ ]8E&J a
     }MyPlaces(自我空间 自由展现)3hN ~ l B m0M4q E
MyPlaces(自我空间 自由展现) Z Y/s-\ J6c$f1M O1B
     public ActionForward execute(ActionMapping mapping, ActionForm form,MyPlaces(自我空间 自由展现)!Z ` Q8\)k2j o P b
               HttpServletRequest request, HttpServletResponse response) {MyPlaces(自我空间 自由展现)9D4l,_)j-k;E&j/r
         LoginForm loginForm = (LoginForm) form;// TODO Auto-generated methodMyPlaces(自我空间 自由展现) V W T ^-c h"o \
                                                         // stubMyPlaces(自我空间 自由展现) A o9w i k w tq L
         User user = new User();
}*q0T C ?/L N+| |5B4RGuest         user.setPassword(loginForm.getPassword());MyPlaces(自我空间 自由展现) ` y }*f5G i)Z
         user.setUsername(loginForm.getUserName());MyPlaces(自我空间 自由展现) | F Q Q X E)p4y
         if (service.isValid(user))MyPlaces(自我空间 自由展现) R.k @4~)B ? B c e
               return mapping.findForward("succeed");
} S _ q N*| M FGuest         else
9X Z$K \2X B C/S n GGuest               return mapping.findForward("fail");
P vr(V {Guest     }MyPlaces(自我空间 自由展现) W J6y4Z B"w
}
5`/z f:Z4h f r.i wGuest至此一个简单的登录已经做成。剩下的工作就是打包并发布你的应用了。