SpringMVC-SSM整合
1 整合思路
Spring整合MyBatis,将MyBatis的实例交给Spring进行管理
Spring整合AOP声明式事务管理
Spring整合SpringMVC,无需额外配置操作
启动tomcat,加载Spring的配置文件
2 SSM整合依赖
- 数据库相关
- mysql驱动依赖
- mybatis依赖
- druid连接池
- Spring整合Mybatis依赖
- Mybatis分页插件依赖
- Mybatis分页插件依赖
- Spring相关
- spring的核心依赖
- springAOP依赖
- spring整合持久层依赖
- spring整合单元测试依赖
- spring声明式事务依赖
- spring织入依赖
aspectjweaver
- springmvc相关的依赖
- JSON交互依赖
jackson-databind
- 文件上传相关依赖
- fileupload 文件上传的依赖
- 依赖排除
- servlet依赖
- jsp依赖
- jstl依赖3个
jstl
standard
jstl-api
- lombok的依赖
lombok
<dependencies>
<!-- mybatis相关的依赖 -->
<!-- mysql驱动依赖 -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.47</version>
</dependency>
<!-- mybatis依赖 -->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.5.4</version>
</dependency>
<!-- druid数据源依赖 -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>1.1.10</version>
</dependency>
<!-- Spring整合Mybatis依赖 -->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis-spring</artifactId>
<version>1.3.2</version>
</dependency>
<!-- Mybatis分页插件依赖 -->
<dependency>
<groupId>com.github.pagehelper</groupId>
<artifactId>pagehelper</artifactId>
<version>5.1.10</version>
</dependency>
<!-- spring相关的依赖 -->
<!-- spring的核心依赖 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>5.3.6</version>
</dependency>
<!-- springAOP依赖 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aspects</artifactId>
<version>5.3.6</version>
</dependency>
<!-- spring整合持久层依赖 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>5.3.6</version>
</dependency>
<!-- spring整合单元测试依赖 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>5.3.6</version>
</dependency>
<!-- spring声明式事务依赖 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
<version>5.3.6</version>
</dependency>
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.9.6</version>
</dependency>
<!-- springmvc相关的依赖 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.3.6</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.12.2</version>
</dependency>
<!-- 文件上传相关依赖 -->
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.4</version>
</dependency>
<!-- fileupload 文件上传的依赖 -->
<dependency>
<groupId>commons-fileupload</groupId>
<artifactId>commons-fileupload</artifactId>
<version>1.3.3</version>
<!-- 依赖排除 -->
<exclusions>
<exclusion>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
</exclusion>
</exclusions>
</dependency>
<!-- servlet依赖 -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.1.0</version>
<scope>provided</scope>
</dependency>
<!--jsp依赖 -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>jsp-api</artifactId>
<version>2.0</version>
<scope>provided</scope>
</dependency>
<!-- jstl依赖 -->
<dependency>
<groupId>javax.servlet.jsp.jstl</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>
<dependency>
<groupId>taglibs</groupId>
<artifactId>standard</artifactId>
<version>1.1.2</version>
</dependency>
<dependency>
<groupId>javax.servlet.jsp.jstl</groupId>
<artifactId>jstl-api</artifactId>
<version>1.2</version>
</dependency>
<!-- lombok的依赖 -->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.18.12</version>
</dependency>
</dependencies>
3 配置文件
3.1 web.xml
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
version="4.0">
<!-- 配置spring监听器 通过监听器其加载spring的配置文件 -->
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:spring/applicationContext-*.xml</param-value>
</context-param>
<!-- 编码过滤器 -->
<filter>
<filter-name>encodingFilter</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<init-param>
<param-name>encoding</param-name>
<param-value>utf-8</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>encodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<!-- 前端控制器 -->
<servlet>
<servlet-name>dispatcherServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:spring/springmvc.xml</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>dispatcherServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
</web-app>
3.2 springmvc配置
- 开启Spring的注解扫描
- 开启SpringMVC的注解扫描
- 配置视图解析器
- 配置文件上传解析器
<?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:context="http://www.springframework.org/schema/context"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/mvc https://www.springframework.org/schema/mvc/spring-mvc.xsd">
<!-- 开启Spring的注解扫描 -->
<context:component-scan base-package="com.ying.controller"/>
<!-- 开启SpringMVC的注解扫描 -->
<mvc:annotation-driven/>
<!-- 配置视图解析器 -->
<bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/pages/"/>
<property name="suffix" value=".jsp"/>
</bean>
<!-- 配置文件上传解析器 -->
<bean class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
<property name="maxUploadSize" value="10000000"/>
<property name="maxUploadSizePerFile" value="2000000"/>
<property name="defaultEncoding" value="utf-8"/>
</bean>
</beans>
3.3 spring-service配置
<?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:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">
<!-- 开启spring注解扫描 扫描service层 -->
<context:component-scan base-package="com.ying"/>
</beans>
3.4 spring-tx配置
<?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:tx="http://www.springframework.org/schema/tx" xmlns:aop="http://www.springframework.org/schema/aop"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/tx
https://www.springframework.org/schema/tx/spring-tx.xsd http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd">
<import resource="classpath:spring/applicationContext-dao.xml"/>
<!-- 配置事务管理器 -->
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<!-- 加载数据源 -->
<property name="dataSource" ref="dataSource"/>
</bean>
<!-- 开启AOP事务扫描 -->
<!-- <tx:annotation-driven transaction-manager="transactionManager"/> -->
<!-- 基于XML配置 -->
<!-- 配置增强类 -->
<tx:advice id="myAdvice" transaction-manager="transactionManager">
<tx:attributes>
<tx:method name="select*" isolation="DEFAULT" propagation="SUPPORTS" timeout="-1"/>
<tx:method name="find*" isolation="DEFAULT" propagation="SUPPORTS" timeout="-1"/>
<tx:method name="get*" isolation="DEFAULT" propagation="SUPPORTS" timeout="-1"/>
<tx:method name="query*" isolation="DEFAULT" propagation="SUPPORTS" timeout="-1"/>
<tx:method name="*" isolation="DEFAULT" propagation="REQUIRED" timeout="-1"/>
</tx:attributes>
</tx:advice>
<!-- 配置切面-->
<aop:config>
<aop:pointcut id="pc" expression="execution(* com.ying.service..*.*(..))"/>
<aop:advisor advice-ref="myAdvice" pointcut-ref="pc"/>
</aop:config>
</beans>
3.5 spring-dao配置
<?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:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">
<!-- SM整合的配置 -->
<!-- 引入外部的配置 -->
<context:property-placeholder location="classpath:mybatis/db.properties"/>
<!-- 数据源配置 -->
<bean id="dataSource" class="com.alibaba.druid.pool.DruidDataSource">
<property name="driverClassName" value="${jdbc.driver}"/>
<property name="url" value="${jdbc.url}"/>
<property name="username" value="${jdbc.username}"/>
<property name="password" value="${jdbc.password}"/>
</bean>
<!-- 配置SqlSessionFactoryBean -->
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<!-- 加载数据源 -->
<property name="dataSource" ref="dataSource"/>
<!-- 加载mybatis配置 -->
<property name="configLocation" value="classpath:mybatis/mybatis-config.xml"/>
</bean>
<!-- 配置Mapper扫描 -->
<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<property name="basePackage" value="com.ying.mapper"/>
</bean>
</beans>
3.6 mybatis配置
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
<!-- 配置Mybatis的日志 -->
<settings>
<setting name="logImpl" value="STDOUT_LOGGING"/>
</settings>
<!-- 设置类型别名 -->
<typeAliases>
<package name="com.ying.pojo"/>
</typeAliases>
<!-- 配置分页插件 -->
<plugins>
<!-- 添加分页拦截器查询 -->
<plugin interceptor="com.github.pagehelper.PageInterceptor"></plugin>
</plugins>
</configuration>
3.7 数据源配置
jdbc.driver=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql:///test
jdbc.username=root
jdbc.password=123456
4 Mapper层
4.1 Mapper接口
public interface EmpMapper {
List<Emp> getAll();
}
4.2 Mapper映射文件
<mapper namespace="com.ying.mapper.EmpMapper">
<select id="getAll" resultType="EmP">
select * from emp
</select>
</mapper>
5 Service层
@Service
public class EmpServiceImpl implements EmpService {
@Autowired
private EmpMapper empMapper;
@Override
public List<Emp> getAll() {
return empMapper.getAll();
}
}
6 Controller层
@Controller
@RequestMapping("/emp")
public class EmpController {
@Autowired
private EmpService empService;
@RequestMapping("/getAll")
public String getAll(Model model){
List<Emp> empList = empService.getAll();
//empList.forEach(System.out::println);
model.addAttribute("empList",empList);
return "empList";
}
}
7 前端JSP
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<table width="80%" align="center" border="1px" cellpadding="10px" cellspacing="0px" bgcolor="#f5f5dc">
<tr>
<th>员工编号</th>
<th>员工图片</th>
<th>员工姓名</th>
<th>员工经理</th>
<th>员工职位</th>
<th>入职日期</th>
<th>员工工资</th>
<th>员工奖金</th>
<th>部门编号</th>
<th>操作</th>
</tr>
<c:forEach items="${empList}" var="emp">
<tr>
<td>${emp.empno}</td>
<td><img src="/${emp.image}" width="100px" height="100px" /></td>
<td>${emp.ename}</td>
<td>${emp.mgr}</td>
<td>${emp.job}</td>
<td><fmt:formatDate value="${emp.hiredate}" pattern="yyyy-MM-dd"></fmt:formatDate> </td>
<td>${emp.sal}</td>
<td>${emp.comm}</td>
<td>${emp.deptno}</td>
<td><a href="/emp/del/${emp.empno}">删除</a><a>修改</a></td>
</tr>
</c:forEach>
</table>
</body>
</html>
8 整合测试
8.1 声明式事务测试
- 在service层编写更新(增删改)操作,然后编写异常代码。测试事务是否生效
8.2 整合后注解扫描问题
此时项目中有两个工厂
- DispatcherServlet 启动的springMVC工厂==负责生产Controller及springMVC自己的系统组件
- ContextLoaderListener 启动的spring工厂==负责生产其他所有组件
- springMVC的工厂会被设置为spring工厂的子工厂,可以随意获取spring工厂中的组件
两个工厂不能有彼此侵入,即,生产的组件不能有重合。
SpringMVC工厂
<!--
use-default-filters :
表示是否使用默认的注解扫描过滤,默认为true,表示使用,包名是什么就扫描哪个包
-->
<context:component-scan base-package="com.ying" use-default-filters="false">
<!-- 指定要扫描的类上的注解 -->
<context:include-filter
type="annotation"
expression="org.springframework.stereotype.Controller"/>
</context:component-scan>
Spring工厂
<context:component-scan base-package="com.ying" use-default-filters="true" >
<!-- 使用默认的注解扫描过滤,但是排除Controller上的注解 -->
<context:exclude-filter
type="annotation"
expression="org.springframework.stereotype.Controller"/>
</context:component-scan>