目的:
通过对ssh框架有了基础性的学习,本文主要是使用注解的方式来简化ssh框架的代码编写。
注意事项:
1、本文提纲:本文通过一个新闻管理系统的实例来简化ssh框架的代码编写,功能包括查询数据库中所有新闻信息,删除某条新闻信息。
2、本项目的搭建环境:Windows 8-64位,Eclipse(开发工具),jdk1.8.0_91,Tomcat 8.0,struts-2.3.30-apps,spring-framework-4.2.2.RELEASE,hibernate-release-5.2.2.Final,mysql数据库
第一步:在eclipse(开发工具)里创建web项目(项目名称:news),并生成web.xml文件。



第二步:导入本次项目要使用到的jar包(struts2、spring4、hibernate5和mysql)。


第三步:在配置文件web.xml配置一个struts2的过滤器和spring监听器。

1 <?xml version="1.0" encoding="UTF-8"?> 2 <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" id="WebApp_ID" version="3.0"> 3 <display-name>news</display-name> 4 <welcome-file-list> 5 <welcome-file>default.jsp</welcome-file> 6 </welcome-file-list> 7 8 <!-- struts2过滤器 --> 9 <filter> 10 <filter-name>struts2</filter-name> 11 <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class> 12 </filter> 13 <filter-mapping> 14 <filter-name>struts2</filter-name> 15 <url-pattern>/*</url-pattern> 16 </filter-mapping>、 17 18 <!-- spring监听器 --> 19 <context-param> 20 <param-name>contextConfigLocation</param-name> 21 <param-value>classpath:applicationContext.xml</param-value> 22 </context-param> 23 <listener> 24 <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> 25 </listener> 26 </web-app>
注:在welcome-file-list这里我添加了一个jsp页面的链接:默认首页<welcome-file>default.jsp</welcome-file>,进行对action的跳转。
第四步:在Java Resources下的src目录下创建四个包(package)进行分层。

第五步:
1、根据数据库表的字段编写News(实体类)放到news.entity包里。

1 package news.entity;
2
3 import java.util.Date;
4
5 import javax.persistence.Column;
6 import javax.persistence.Entity;
7 import javax.persistence.GeneratedValue;
8 import javax.persistence.GenerationType;
9 import javax.persistence.Id;
10 import javax.persistence.Table;
11
12 /*
13 * 跟数据库表一致,作为一个java对象
14 * 1个对象代表的是数据库表中的一行记录
15 * 1个属性代表的是表中的一个字段
16 */
17 @Entity //声明当前类为hibernate映射到数据库中的实体类
18 @Table(name="news") //声明table的名称
19 public class News {
20 @Id //声明此列为主键,作为映射对象的标识符
21 @GeneratedValue(strategy = GenerationType.AUTO)
22 private Integer id;
23
24 @Column(name="title",nullable=false)
25 private String title;
26
27 @Column(name="content",nullable=false)
28 private String content;
29
30 @Column(name="begintime",nullable=false)
31 private Date begintime;
32
33 @Column(name="username",nullable=false)
34 private String username;
35
36 public News() {
37 super();
38 }
39
40 public Integer getId() {
41 return id;
42 }
43 public void setId(Integer id) {
44 this.id = id;
45 }
46
47 public String getTitle() {
48 return title;
49 }
50 public void setTitle(String title) {
51 this.title = title;
52 }
53
54 public String getContent() {
55 return content;
56 }
57 public void setContent(String content) {
58 this.content = content;
59 }
60
61 public Date getBegintime() {
62 return begintime;
63 }
64 public void setBegintime(Date begintime) {
65 this.begintime = begintime;
66 }
67
68 public String getUsername() {
69 return username;
70 }
71 public void setUsername(String username) {
72 this.username = username;
73 }
74
75
76 }
注:在实体类未用到注解前,我们需要编写一个映射文件,使用注解后就可以将原来的映射文件删除。
2、在news.service包里编写NewsService(接口类)和NewsServiceImpl(实现类)。

NewsService(接口类):
1 package news.service;
2
3 import java.util.List;
4
5 //创建一个NewsService接口类
6 public interface NewsService {
7
8 public List showAllNews();
9
10 public String findNews();
11
12 public String deleteSingleNews(Integer id);
13 }
NewsServiceImpl(实现类):
1 package news.service;
2
3 import java.util.List;
4
5 import org.springframework.beans.factory.annotation.Autowired;
6 import org.springframework.context.annotation.Scope;
7 import org.springframework.stereotype.Service;
8
9 import news.dao.NewsDao;
10 import news.entity.News;
11
12 //创建NewsServiceImpl(实现类)实现NewsService接口
13 //使用@Service类注解自动注入,并且作用域范围为非单例
14 @Service
15 @Scope("prototype")
16 public class NewsServiceImpl implements NewsService {
17
18 //使用spring内置注解@Autowired自动注入实例
19 @Autowired
20 private NewsDao nd;
21
22 @Override
23 public List showAllNews() {
24
25 //调用NewsDao的showAllNews方法存入到List<News>集合里
26 List<News> allNewList=nd.showAllNews();
27 //返回List集合
28 return allNewList;
29 }
30
31 @Override
32 public String findNews() {
33 // TODO Auto-generated method stub
34 return null;
35 }
36
37 @Override
38 public String deleteSingleNews(Integer id) {
39
40 //定义一个字符串保存到returnValue变量里
41 String returnValue="deleteFailed";
42
43 //调用NewsDao的deleteSingleNews方法
44 returnValue=nd.deleteSingleNews(id);
45
46 //返回returnValue
47 return returnValue;
48 }
49
50 }
3、在news.dao包里编写NewsDao(接口类)和NewsDaoImpl(实现类)。

NewsDao(接口类):
1 package news.dao;
2
3 import java.util.List;
4
5 //创建NewsDao(接口类)
6 public interface NewsDao {
7
8 public List showAllNews();
9
10 public String findNews();
11
12 public String deleteSingleNews(Integer id);
13 }
NewsDaoImpl(实现类):
1 package news.dao;
2
3 import java.util.List;
4
5 import org.hibernate.Session;
6 import org.hibernate.SessionFactory;
7 import org.hibernate.query.Query;
8 import org.springframework.beans.factory.annotation.Autowired;
9 import org.springframework.context.annotation.Scope;
10 import org.springframework.stereotype.Repository;
11
12 import news.entity.News;
13
14 //创建NewsDaoImpl(实现类)实现NewsDao接口
15 //使用@Repository类注解自动注入,并且作用域范围为非单例
16 @Repository
17 @Scope("prototype")
18 public class NewsDaoImpl implements NewsDao {
19
20 //使用spring内置注解@Autowired自动注入实例
21 @Autowired
22 private SessionFactory sf;
23
24 @Override
25 public List showAllNews() {
26 //重新建立一个新的session
27 Session session=sf.openSession();
28 //创建Query
29 Query query=session.createQuery("from News");
30
31 //将结果集保存到List<News>集合里
32 List<News> allNewList=query.getResultList();
33
34 //关闭session
35 session.close();
36
37 //返回List<News>集合
38 return allNewList;
39 }
40
41 @Override
42 public String findNews() {
43 // TODO Auto-generated method stub
44 return null;
45 }
46
47 @Override
48 public String deleteSingleNews(Integer id) {
49 //重新建立一个新的session
50 Session session=sf.openSession();
51 //创建Query并将id值设置为传过来的参数值
52 Query query=session.createQuery("from News where id=:myid");
53 query.setParameter("myid", id);
54 //将结果集保存到List<News>集合里
55 List<News> deleteList=query.getResultList();
56
57 //判断deleteList有没有值,如果有,则执行下面的语句,如果没有,则什么都不做
58 if(deleteList.size()==1){
59 //获取deleteList中的值并保存到News对象中
60 News news=deleteList.get(0);
61 //在控制台输出:删除对象和id值
62 System.out.println("删除对象:"+news.getTitle()+" Id:"+news.getId());
63 //创建事务
64 session.getTransaction().begin();
65 //删除对象
66 session.delete(news);
67 //提交事务
68 session.getTransaction().commit();
69 //关闭session
70 session.close();
71 }
72
73 //返回字符串deleteOK
74 return "deleteOK";
75 }
76
77 }
4、编写NewsAction(action类)。

1 package news.action;
2
3 import java.util.List;
4
5 import org.springframework.beans.factory.annotation.Autowired;
6 import org.springframework.context.annotation.Scope;
7 import org.springframework.stereotype.Controller;
8
9 import com.opensymphony.xwork2.ActionSupport;
10
11 import news.entity.News;
12 import news.service.NewsService;
13
14 //创建NewsAction(action类)继承ActionSupport接口
15 //使用@Controller类注解自动注入,并且作用域范围为非单例
16 @Controller
17 @Scope("prototype")
18 public class NewsAction extends ActionSupport {
19
20 //获取从客户端传递过来的值
21 private Integer id;
22
23 //strtus自动的赋值
24 public void setId(Integer id) {
25 this.id = id;
26 }
27
28 //使用spring内置注解@Autowired自动注入实例
29 @Autowired
30 private NewsService ns;
31
32 private List<News> allNewList;
33
34 public List<News> getAllNewList() {
35 return allNewList;
36 }
37
38 public void setAllNewList(List<News> allNewList) {
39 this.allNewList = allNewList;
40 }
41
42 //查询出所有数据
43 public String showAllNews(){
44
45 allNewList=ns.showAllNews();
46
47 return "success";
48 }
49
50 //查询单条数据(本例未使用)
51 public String findNews(){
52
53 return "";
54 }
55
56 //删除某条数据
57 public String deleteSingleNews(){
58
59 System.out.println("客户端传过来的id值是:"+id);
60
61 String returnValue=ns.deleteSingleNews(id);
62
63 return returnValue;
64 }
65 }
第六步:编写struts.xml(struts配置文件)、applicationContext.xml(spring配置文件)、jdbc.properties(外部属性文件)。
注:将这些配置文件放到src里。

struts.xml:
1 <?xml version="1.0" encoding="UTF-8"?>
2 <!DOCTYPE struts PUBLIC
3 "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"
4 "http://struts.apache.org/dtds/struts-2.3.dtd">
5 <!-- 上面的头,注意版本,从样例里复制过来 showcase.war\WEB-INF\src\java\struts.xml -->
6
7 <struts>
8 <!-- 告知Struts2运行时使用Spring来创建对象 -->
9 <constant name="struts.objectFactory" value="spring"></constant>
10 <!-- 第1步:先定义一个包 -->
11 <package name="mynews" extends="struts-default">
12 <!-- 第2步:定义一个action,配置跳转信息 name 类似于Servlet 注:这里使用了通配符来指定调用的方法-->
13 <action name="NewsAction_*" class="newsAction" method="{1}">
14 <!-- 跳转是forward/WEB-INF/是防止jsp不经过action就可以访问-->
15 <!-- result接收返回的字符串,然后做对应的事情 -->
16 <result name="success">/WEB-INF/jsp/NewsIndex.jsp</result>
17 <!-- 删除后通过type="redirectAction"这个类型重新跳转到NewsAction_showAllNews.action刷新页面 -->
18 <result name="deleteOK" type="redirectAction">NewsAction_showAllNews.action</result>
19 </action>
20 </package>
21 </struts>
applicationContext.xml:
1 <?xml version="1.0" encoding="UTF-8"?>
2 <beans xmlns="http://www.springframework.org/schema/beans"
3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:p="http://www.springframework.org/schema/p"
4 xmlns:aop="http://www.springframework.org/schema/aop" xmlns:context="http://www.springframework.org/schema/context"
5 xmlns:jee="http://www.springframework.org/schema/jee" xmlns:tx="http://www.springframework.org/schema/tx"
6 xsi:schemaLocation="
7 http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.2.xsd
8 http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.2.xsd
9 http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.2.xsd
10 http://www.springframework.org/schema/jee http://www.springframework.org/schema/jee/spring-jee-4.2.xsd
11 http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.2.xsd">
12
13 <!-- spring注解解析器 -->
14 <context:component-scan base-package="news"></context:component-scan>
15
16 <!-- 引入外部属性文件 -->
17 <context:property-placeholder location="classpath:jdbc.properties" />
18 <!-- 添加sessionFactory bane ,注意,该类是Spring提供的 -->
19 <bean id="sessionFactory"
20 class="org.springframework.orm.hibernate5.LocalSessionFactoryBean" scope="prototype">
21 <!-- 注入连接池,包含了数据库用户名,密码等等信息 -->
22 <property name="dataSource" ref="myDataSource" />
23
24 <!-- 配置Hibernate的其他的属性 -->
25 <property name="hibernateProperties">
26 <props>
27 <prop key="hibernate.dialect">org.hibernate.dialect.MySQL5Dialect</prop>
28 <prop key="hibernate.show_sql">true</prop>
29 <prop key="hibernate.format_sql">true</prop>
30 <prop key="hibernate.connection.autocommit">false</prop>
31 <!-- 开机自动生成表 -->
32 <prop key="hibernate.hbm2ddl.auto">update</prop>
33 </props>
34 </property>
35 <!-- 扫描实体类包,解析实体类的注解 -->
36 <property name="packagesToScan">
37 <list>
38 <!-- value值填写实体类所在的包 -->
39 <value>news.entity</value>
40 </list>
41 </property>
42 </bean>
43
44 <!-- 添加c3p0数据库连接池 bean -->
45 <bean id="myDataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
46 <!-- 数据库连接配置 -->
47 <property name="driverClass" value="${jdbc.driver}" />
48 <property name="jdbcUrl" value="${jdbc.url}" />
49 <property name="user" value="${jdbc.user}" />
50 <property name="password" value="${jdbc.password}" />
51 <!-- 每300秒检查所有连接池中的空闲连接 -->
52 <property name="idleConnectionTestPeriod" value="300"></property>
53 <!-- 最大空闲时间,900秒内未使用则连接被丢弃。若为0则永不丢弃 -->
54 <property name="maxIdleTime" value="900"></property>
55 <!-- 最大连接数 -->
56 <property name="maxPoolSize" value="2"></property>
57 </bean>
58 </beans>
59
jdbc.properties(外不属性文件):
1 jdbc.driver=com.mysql.jdbc.Driver 2 jdbc.url=jdbc:mysql://localhost:3306/news 3 jdbc.user=root 4 jdbc.password=123456
第七步:创建一个NewsIndex.jsp页面将所有数据取出来显示到页面上和一个default.jsp页面进行action跳转。

NewsIndex.jsp:
1 <%@ page language="java" contentType="text/html; charset=UTF-8"
2 pageEncoding="UTF-8"%>
3 <%@ taglib uri="/struts-tags" prefix="s" %>
4 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
5 <html>
6 <head>
7 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
8 <title>Insert title here</title>
9 <style>
10 #showDiv{
11 width:1000px;
12 height:70px;
13 margin: auto;
14 }
15 </style>
16 </head>
17 <body>
18 <div id="showDiv" align="center">
19 <h1>新闻管理系统</h1>
20 </div>
21 <div id="msgDiv" align="center">
22 <table border="1" id="#msgTab">
23 <tr>
24 <th>序号</th>
25 <th>标题</th>
26 <th>内容</th>
27 <th>办卡日期</th>
28 <th>姓名</th>
29 <th>操作</th>
30 </tr>
31 <s:iterator value="allNewList">
32 <tr>
33 <td><s:property value="id"/></td>
34 <td><s:property value="title"/></td>
35 <td><s:property value="content"/></td>
36 <td><s:date name="begintime" format="yyyy年MM月dd日"/></td>
37 <td><s:property value="username"/></td>
38 <td><s:a value="NewsAction_deleteSingleNews?id=%{id}">删除</s:a></td>
39 </tr>
40 </s:iterator>
41 <s:if test="allNewList.size()==0">
42 <tr>
43 <td colspan="6">没有查找到数据</td>
44 </tr>
45 </s:if>
46 </table>
47 </div>
48 </body>
49 </html>
default.jsp:
1 <%@ page language="java" contentType="text/html; charset=UTF-8"
2 pageEncoding="UTF-8"%><%
3 /* 跳转到NewsAction_showAllNews.action */
4 response.sendRedirect("NewsAction_showAllNews.action");
5 %>
运行查询结果:
浏览器显示:

控制台输出:

运行删除结果:
浏览器显示:

控制台输出(删除后再查询结果):

总结:通过对本例项目搭建到功能的编写,使用注解的方式简化了ssh框架代码编写,对实例和类直接用注解注入。
来源:https://www.cnblogs.com/laibin/p/5966789.html