前面整理了IOC、AOP的实现方式,今天称热打铁复习一下SpringDAO。
JdbcTemplate
SpringDAO的核心类是JdbcTemplate,全限定名为org.springframework.jdbc.core.JdbcTemplate。可能你会看到JdbcDaoSupport这个类也是里边的核心,但是其实JdbcDaoSupport这个类里边有一个类型为JdbcTemplate的属性,最后执行sql语句的时候还是用的JdbcDaoSupport的getJdbcTemplate()方法得到JdbcTemplate之后再通过JdbcTemplate类的方法来执行。
JdbcTemplate对JDBC的差别在哪?
JDBC需要每次进行数据库连接, 然后处理SQL语句,传值,关闭数据库。
甚至有时还可能会出现数据库忘记关闭导致连接被占用。
在以后的工作中,客户的需求肯定不是一成不变的,这就导致经常会改动数据库内容.
通过JDBCtemplate我们只需更改需要更改的那一部分内容就可以了,不需要进行全局修改。Spring将替我们完成所有的JDBC底层细节处理工作。
JdbcTemplate主要提供以下五类方法:
- execute方法:可以用于执行任何SQL语句,一般用于执行DDL语句;
- update方法及batchUpdate方法:update方法用于执行新增、修改、删除等语句; * batchUpdate方法用于执行批处理相关语句;
- query方法及queryForXXX方法:用于执行查询相关语句;
- call方法:用于执行存储过程、函数相关语句。
SpringDAO的实现
建立表格:1
2
3
4
5
6
7
8CREATE TABLE `students` (
`student_id` int(11) NOT NULL AUTO_INCREMENT,
`student_name` varchar(20) NOT NULL,
`student_sex` char(1) DEFAULT NULL,
`student_birthday` date DEFAULT NULL,
`group_id` varchar(20) DEFAULT NULL,
PRIMARY KEY (`student_id`)
) ENGINE=InnoDB AUTO_INCREMENT=9 DEFAULT CHARSET=utf8;
POJO:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64package com.aowin.testspring.dao.pojo;
import java.io.Serializable;
import java.sql.Date;
public class Students implements Serializable {
private Integer studentid;
private String studentname;
private String studentsex;
private Date studentbirthday;
private String groupid;
public Students() {
}
public Integer getStudentid() {
return studentid;
}
public void setStudentid(Integer studentid) {
this.studentid = studentid;
}
public String getStudentname() {
return studentname;
}
public void setStudentname(String studentname) {
this.studentname = studentname;
}
public String getStudentsex() {
return studentsex;
}
public void setStudentsex(String studentsex) {
this.studentsex = studentsex;
}
public Date getStudentbirthday() {
return studentbirthday;
}
public void setStudentbirthday(Date studentbirthday) {
this.studentbirthday = studentbirthday;
}
public String getGroupid() {
return groupid;
}
public void setGroupid(String groupid) {
this.groupid = groupid;
}
@Override
public String toString() {
return "Students [studentid=" + studentid + ", studentname=" + studentname + ", studentsex=" + studentsex
+ ", studentbirthday=" + studentbirthday + ", groupid=" + groupid + "]";
}
}
DAO接口:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31package com.aowin.testspring.dao;
import java.util.List;
import com.aowin.testspring.dao.pojo.Students;
public interface IStudentDAO {
String INSERT_STUDENT_SQL = "insert into students (student_name,student_sex,student_birthday,group_id)" +
"values(?,?,?,?)";
String SELECT_STUDENT_ALL_SQL ="select student_id,student_name,student_sex,student_birthday,group_id from students";
String SELECT_STUDENT_COUNT_SQL ="select count(student_id) total from students";
/**
* 添加学生信息
* @param student学生信息
* @return 是否添加成功
*/
public boolean insertStudent(Students student);
/**
* 获取所有学生信息
* @return 所有学生信息
*/
public List<Students> selectStudents();
/**
* 获取学生总人数
* @return
*/
public int selectTotalRocords();
}
SpringDAO的实现有两种方式。
继承JdbcDaoSupport
我们写一个实现类实现IStudentDAO接口,并且继承JdbcDaoSupport类:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51package com.aowin.testspring.dao;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.RowMapper;
import org.springframework.jdbc.core.support.JdbcDaoSupport;
import org.springframework.jdbc.datasource.DriverManagerDataSource;
import com.aowin.testspring.dao.pojo.Students;
public class StudentDAOImpl0 extends JdbcDaoSupport implements IStudentDAO {
public StudentDAOImpl0() {
// TODO Auto-generated constructor stub
}
//实现数据添加方法
public boolean insertStudent(Students student) {
boolean result = false;
//通过update方法执行接口中的SQL语句,并且将SQL语句参数传递进去
int i = super.getJdbcTemplate().update(INSERT_STUDENT_SQL,student.getStudentname(),
student.getStudentsex(),student.getStudentbirthday(),student.getGroupid());
//如果成功添加
if(i > 0)
result = true;
return false;
}
//实现获取所有学生信息方法
public List<Students> selectStudents() {
//通过query方法执行接口中的SQL语句,并封装返回的数据
return super.getJdbcTemplate().query(SELECT_STUDENT_ALL_SQL, new RowMapper<Students>() {
//封装数据返回的数据
public Students mapRow(ResultSet rs, int rowNum) throws SQLException {
Students student = new Students();
student.setGroupid(rs.getString("group_id"));
student.setStudentbirthday(rs.getDate("student_birthday"));
student.setStudentname(rs.getString("student_name"));
student.setStudentsex(rs.getString("student_sex"));
return student;
}
});
}
//实现获取全部学生数方法
public int selectTotalRocords() {
//通过queryForObject方法执行接口中的SQL语句,并声明返回类型。
return super.getJdbcTemplate().queryForObject(SELECT_STUDENT_COUNT_SQL, Integer.class);
}
}
程序中所做的事无非就是执行JdbcTemplate的方法在执行SQL语句,其操作和JDBC对比起来,程序并不需要考虑与数据库的连接获取、关闭数据库连接等事情,只需执行我们的SQL语句即可。
配置文件:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19<!-- 配置数据源 -->
<bean id="dmds" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<!-- 数据库连接所必要的数据 -->
<!-- 数据库驱动 -->
<property name="driverClassName" value="com.mysql.jdbc.Driver"></property>
<!-- 数据库url -->
<property name="url" >
<value>jdbc:mysql://localhost:3306/testmybatis?useUnicode=true&characterEncoding=utf8</value>
</property>
<!-- 用户名 -->
<property name="username" value="root"></property>
<!-- 密码 -->
<property name="password" value="123"></property>
</bean>
<!-- 配置测试类,将数据源注入-->
<bean id="studentDao" class="com.aowin.testspring.dao.StudentDAOImpl0">
<property name="dataSource" ref="dmds"></property>
</bean>
在配置文件中我们可以看到,因为要连接数据库,我们对数据源的配置是必不可少的。我们需要配置DriverManagerDataSource类,并且给它注入连接数据库必须的属性(DriverManager、url、username、password)。看到配置文件可能有人会疑惑,StudentDAOImpl0这个类并没有dataSource属性,为何可以注入数据源呢?其实我们继承的JdbcDaoSupport类中有 setDataSource(DataSource dataSource) 方法,所以我们可以直接执行注入操作。在SpringDAO低耦合操作中,我们可以不再继承JdbcDaoSupport,而是直接设置JdbcTemplate属性并增加相应的set/get方法。
测试类中(这里我们只测试InsertStudent()方法):1
2
3
4
5
6
7
8
9
10
11
12@Test
public void test(){
ClassPathXmlApplicationContext context =
new ClassPathXmlApplicationContext("springJDBC.xml");
IStudentDAO studentDao = context.getBean("studentDao",IStudentDAO.class);
Students students = new Students();
students.setStudentname("德莱文");
students.setStudentsex("1");
students.setStudentbirthday(java.sql.Date.valueOf("2014-10-1"));
students.setGroupid("S3");
studentDao.insertStudent(students);
}
运行结果:
可以看到数据成功的插入。
低耦合方式
低耦合的实现方式中,我们不再继承JdbcDaoSupport类,而是给我们的实现类设置JdbcTemplate接口。
也就是在前面的这种实现方式中添加:1
2
3
4
5
6
7
8
9
10@Autowired
private JdbcTemplate template;
public StudentDAOImpl() {
// TODO Auto-generated constructor stub
}
public JdbcTemplate getTemplate() {
return template;
}
并且不再继承JdbcDaoSupport。再修改实现类类名为:StudentDAOImpl
在配置文件中:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21<!-- 开启注解 -->
<context:annotation-config />
<!-- 配置数据源 -->
<bean id="dmds" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<!-- 数据库连接所必要的数据 -->
<property name="driverClassName" value="com.mysql.jdbc.Driver"></property>
<property name="url" >
<value>jdbc:mysql://localhost:3306/testmybatis?useUnicode=true&characterEncoding=utf8</value>
</property>
<property name="username" value="root"></property>
<property name="password" value="123"></property>
</bean>
<!-- 配置JdbcTemplate -->
<bean id="template" class="org.springframework.jdbc.core.JdbcTemplate">
<constructor-arg index="0" ref="dmds"></constructor-arg>
</bean>
<!-- 声明实现类 -->
<bean id="studentDao" class="com.aowin.testspring.dao.StudentDAOImpl">
</bean>
JdbcTemplate中也需要注入dataSource属性,我们这里采用构造器注入。
在测试方法中(这里只测试insertStudent()方法):1
2
3
4
5
6
7
8
9
10
11
12@Test
public void test1(){
ClassPathXmlApplicationContext context =
new ClassPathXmlApplicationContext("springJDBC2.xml");
IStudentDAO studentDao = context.getBean("studentDao",IStudentDAO.class);
Students students = new Students();
students.setStudentname("盖伦");
students.setStudentsex("1");
students.setStudentbirthday(java.sql.Date.valueOf("2012-10-1"));
students.setGroupid("s1");
studentDao.insertStudent(students);
}
执行结果:
可以看到方法执行成功。
说到SpringDAO不得不提到Spring中的事务处理,因为内容比较多我们再另起一篇。
Spring的事务处理