Spring笔记(第五弹:Spring MVC工程集成Mybatis)

上一篇中我们已经搭建了一个Spring MVC工程,现在我们在此基础上来集成Mybatis。

配置pom.xml

还是到http://mvnrepository.org/上面来找依赖。

spring-jdbc

搜索spring jdbc,我们选用4.3.4版本,依赖如下:

<!-- https://mvnrepository.com/artifact/org.springframework/spring-jdbc -->
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-jdbc</artifactId>
    <version>4.3.4.RELEASE</version>
</dependency>

mysql-connector-java

搜索mysql,找到MySQL Connector/J,我们选用6.0.5版本,依赖如下:

<!-- https://mvnrepository.com/artifact/mysql/mysql-connector-java -->
<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>6.0.5</version>
</dependency>

commons-dbcp

搜索commons dbcp,我们选用1.4版本,依赖如下:

<!-- https://mvnrepository.com/artifact/commons-dbcp/commons-dbcp -->
<dependency>
    <groupId>commons-dbcp</groupId>
    <artifactId>commons-dbcp</artifactId>
    <version>1.4</version>
</dependency>

mybatis-spring

搜索mybatis spring,我们选用1.3.0,依赖如下:

<!-- https://mvnrepository.com/artifact/org.mybatis/mybatis-spring -->
<dependency>
    <groupId>org.mybatis</groupId>
    <artifactId>mybatis-spring</artifactId>
    <version>1.3.0</version>
</dependency>

mybatis

搜索mybatis,我们选用3.3.0,依赖如下:

<!-- https://mvnrepository.com/artifact/org.mybatis/mybatis -->
<dependency>
    <groupId>org.mybatis</groupId>
    <artifactId>mybatis</artifactId>
    <version>3.3.0</version>
</dependency>

pom.xml完整配置

至此,pom.xml文件就配置好了 ,完整配置如下:

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>com.demo</groupId>
    <artifactId>mavenSpringDemo</artifactId>
    <packaging>war</packaging>
    <version>0.0.1-SNAPSHOT</version>
    <name>mavenSpringDemo Maven Webapp</name>
    <url>http://maven.apache.org</url>
    <dependencies>
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>3.8.1</version>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>javax.servlet-api</artifactId>
            <version>3.1.0</version>
            <scope>provided</scope>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-webmvc</artifactId>
            <version>4.3.4.RELEASE</version>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-jdbc</artifactId>
            <version>4.3.4.RELEASE</version>
        </dependency>
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>6.0.5</version>
        </dependency>
        <dependency>
            <groupId>commons-dbcp</groupId>
            <artifactId>commons-dbcp</artifactId>
            <version>1.4</version>
        </dependency>
        <dependency>
            <groupId>org.mybatis</groupId>
            <artifactId>mybatis-spring</artifactId>
            <version>1.3.0</version>
        </dependency>
        <dependency>
            <groupId>org.mybatis</groupId>
            <artifactId>mybatis</artifactId>
            <version>3.3.0</version>
        </dependency>
    </dependencies>
    <build>
        <finalName>mavenSpringDemo</finalName>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>3.3</version>
                <configuration>
                    <source>1.8</source>
                    <target>1.8</target>
                </configuration>
            </plugin>
        </plugins>
    </build>
</project>

创建业务代码

创建entity

新建com.demo.entity包,新建User类,(数据库中自然是要建相应的user表,这个这里就不说了。)完整代码如下:

package com.demo.entity;

public class User {

    private int id;

    private String name;

    private String password;

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getPassword() {
        return password;
    }

    public void setPassword(String password) {
        this.password = password;
    }

    @Override
    public String toString() {
        return "User [id=" + id + ", name=" + name + ", password=" + password + "]";
    }

}

创建DAO接口和实现

新建com.demo.dao包,新建UserDAO接口,完整代码如下:

package com.demo.dao;

import com.demo.entity.User;

public interface UserDAO {
    public User selectById(int id);
}

新建com.demo.dao.impl包,新建UserDAOImpl类,完整代码如下:

package com.demo.dao.impl;

import javax.annotation.Resource;

import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.support.SqlSessionDaoSupport;
import org.springframework.stereotype.Repository;

import com.demo.dao.UserDAO;
import com.demo.entity.User;

@Repository
public class UserDAOImpl extends SqlSessionDaoSupport implements UserDAO {

    @Resource
    public void setSqlSessionFactory(SqlSessionFactory sqlSessionFactory) {
        super.setSqlSessionFactory(sqlSessionFactory);
    }

    @Override
    public User selectById(int id) {
        return this.getSqlSession().selectOne("com.demo.UserMapper.selectById", id);
    }

}

创建Service的接口和实现

新建com.demo.service包,新建UserService接口,完整代码如下:

package com.demo.service;

import com.demo.entity.User;

public interface UserService {
    public User selectById(int id);
}

新建com.demo.service.impl包,新建UserServiceImpl类,完整代码如下:

package com.demo.service.impl;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.demo.dao.UserDAO;
import com.demo.entity.User;
import com.demo.service.UserService;

@Service
public class UserServiceImpl implements UserService {

    @Autowired
    private UserDAO userDAO;

    @Override
    public User selectById(int id) {
        return userDAO.selectById(id);
    }

}

修改Controller

上一篇中我们已经新建了com.demo.web包, 以及UserController类,现在我们修改一下,完整代码如下:

package com.demo.web;

import java.io.IOException;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;

import com.demo.service.UserService;

@Controller
public class UserController {

    @Autowired
    private UserService userService;

    @RequestMapping("/sayHello")
    public void sayHello(HttpServletRequest request, HttpServletResponse response) throws IOException {
        response.getWriter().write(userService.selectById(1).toString());
    }
}

创建Mapper

在resources下新建目录/config/mappers,新建UserMapper.xml,内容如下:

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd" >

<mapper namespace="com.demo.UserMapper">
    <select id="selectById" resultType="com.demo.entity.User">
        select * from user where id = #{id}
    </select>
</mapper>

配置applicationContext.xml

配置包扫描

我们扫描com.demo包下所有的类,

<context:component-scan base-package="com.demo" />

但是之前在spring-mvc.xml里已经扫描过com.demo.web,这个包里面都是用@Controller注解的controller类,为了不重复扫描,我们把它排除:

<context:component-scan base-package="com.demo">
    <context:exclude-filter type="annotation"
        expression="org.springframework.stereotype.Controller" />
</context:component-scan>

配置dataSource

<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
        destroy-method="close">
    <property name="driverClassName" value="com.mysql.cj.jdbc.Driver"></property>
    <property name="url" value="jdbc:mysql://localhost:3306/test?serverTimezone=UTC"></property>
    <property name="username" value="root"></property>
    <property name="password" value=""></property>
</bean>

配置sessionFactory

<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
    <property name="dataSource" ref="dataSource" />
    <property name="mapperLocations" value="classpath:config/mappers/**/*.xml" />
</bean>

配置tx:annotation-driven

<tx:annotation-driven transaction-manager="transactionManager" />

配置transactionManager

<bean id="transactionManager"
        class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
    <property name="dataSource" ref="dataSource" />
</bean>

applicationContext.xml完整配置

至此,applicationContext.xml就配置好了,完整配置如下:

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:p="http://www.springframework.org/schema/p"
    xmlns:context="http://www.springframework.org/schema/context" xmlns:tx="http://www.springframework.org/schema/tx"
    xsi:schemaLocation="http://www.springframework.org/schema/beans  
                        http://www.springframework.org/schema/beans/spring-beans.xsd  
                        http://www.springframework.org/schema/context  
                        http://www.springframework.org/schema/context/spring-context.xsd  
                        http://www.springframework.org/schema/tx  
                        http://www.springframework.org/schema/tx/spring-tx.xsd">

    <context:component-scan base-package="com.demo">
        <context:exclude-filter type="annotation"
            expression="org.springframework.stereotype.Controller" />
    </context:component-scan>

    <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
        destroy-method="close">
        <property name="driverClassName" value="com.mysql.cj.jdbc.Driver"></property>
        <property name="url" value="jdbc:mysql://localhost:3306/test?serverTimezone=UTC"></property>
        <property name="username" value="root"></property>
        <property name="password" value=""></property>
    </bean>

    <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
        <property name="dataSource" ref="dataSource" />
        <property name="mapperLocations" value="classpath:config/mappers/**/*.xml" />
    </bean>

    <tx:annotation-driven transaction-manager="transactionManager" />
    <bean id="transactionManager"
        class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
        <property name="dataSource" ref="dataSource" />
    </bean>
</beans>

配置web.xml

配置contextConfigLocation

<context-param>
    <param-name>contextConfigLocation </param-name>
    <param-value>classpath:applicationContext.xml </param-value>
</context-param>

配置contextLoaderListener

<listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>

web.xml完整配置

web.xml里的其他配置在上一篇中已经配过了,完整配置如下:

<!DOCTYPE web-app PUBLIC
 "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
 "http://java.sun.com/dtd/web-app_2_3.dtd" >

<web-app>
    <display-name>Archetype Created Web Application</display-name>

    <context-param>
        <param-name>contextConfigLocation </param-name>
        <param-value>classpath:applicationContext.xml </param-value>
    </context-param>

    <listener>
        <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
    </listener>

    <servlet>
        <servlet-name>SpringMVC</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <init-param>
            <param-name>contextConfigLocation</param-name>
            <param-value>classpath:spring-mvc.xml</param-value>
        </init-param>
        <load-on-startup>1</load-on-startup>
    </servlet>
    <servlet-mapping>
        <servlet-name>SpringMVC</servlet-name>
        <url-pattern>/</url-pattern>
    </servlet-mapping>
</web-app>

至此,Spring MVC工程集成Mybatis完毕。

测试

测试基本功能

测试一下基本功能,启动tomcat,访问http://localhost:8080/mavenSpringDemo/sayHello,网页上能显示出user相关信息表示测试成功。

测试事务

测试一下事务是否有效。之前我们在applicationContext.xml里已经配置好了事务相关的配置:

<tx:annotation-driven transaction-manager="transactionManager" />
<bean id="transactionManager"
    class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
    <property name="dataSource" ref="dataSource" />
</bean>

现在我们就增加一些业务代码。
在UserMapper.xml里增加一个方法:

<insert id="insert" parameterType="com.demo.entity.User">
    insert user(id, name, password) values(#{id}, #{name}, #{password})
</insert>

在UserDAO.java里增加一个接口方法:

public int insert(User user);

在UserDAOImpl.java里增加一个实现方法:

@Override
public int insert(User user) {
    return this.getSqlSession().insert("com.demo.UserMapper.insert", user);
}

在UserService.java里增加一个接口方法:

public int insert(User user);

在UserServiceImpl.java里增加一个实现方法:

@Override
@Transactional
public int insert(User user) {
    userDAO.insert(user);
    throw new RuntimeException();
}

注意,这个方法上写上@Transactional注解,表示这个方法我们要进行事务的控制。调用insert方法以后直接抛出异常用来测试事务是否有效。如果事务有效,那么insert方法将会回滚,也就是说数据不会插到数据库里去。
在UserController.java里增加方法:

@RequestMapping("/insert")
public void insert(HttpServletResponse response) throws IOException {
    User user = new User();
    user.setId(10);
    user.setName("name10");
    user.setPassword("123456");
    String result = "";
    try {
        result = userService.insert(user) + "";
    } catch (RuntimeException e) {
        result = "roll back";
    }
    response.getWriter().write(result);
}

最后我们测试一下,启动tomcat,访问http://localhost:8080/mavenSpringDemo/insert,网页上能显示出“roll back”,并且数据库中User表里并没有插入这条数据表示测试事务成功。

常见问题

问题:
在访问页面的时候,如果出现如下错误:
Error querying database. Cause: org.springframework.jdbc.CannotGetJdbcConnectionException: Could not get JDBC Connection; nested exception is org.apache.commons.dbcp.SQLNestedException: Cannot create PoolableConnectionFactory (The server time zone value ‘?й???????’ is unrecognized or represents more than one time zone. You must configure either the server or JDBC driver (via the serverTimezone configuration property) to use a more specifc time zone value if you want to utilize time zone support.)
解决方案:
报这个错说明是时区设置有误,需要在applicationContext.xml中配置dataSource时,在url后面加上时区的设置serverTimezone=UTC,url如下:
jdbc:mysql://localhost:3306/test?serverTimezone=UTC

问题:
tomcat启动时报错:Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Property ‘sqlSessionFactory’ or ‘sqlSessionTemplate’ are required
解决方案:
在DAO的实现类或是DAO继承的DAO基类中(在我们的工程中即为UserDAOImpl)加上如下代码:

@Resource
public void setSqlSessionFactory(SqlSessionFactory sqlSessionFactory) {
    super.setSqlSessionFactory(sqlSessionFactory);
}

问题:
tomcat启动时报错: IOException parsing XML document from ServletContext resource [/WEB-INF/applicationContext.xml];
解决方法:
在web.xml中加入这些配置:

<context-param>
    <param-name>contextConfigLocation </param-name>
    <param-value>classpath:applicationContext.xml </param-value>
</context-param>
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值