一、初识SpringMVC
ssm
:mybatis
+Spring
+SpringMVC
1.1 什么是MVC
MVC:是一种软件设计规范,是将业务逻辑、数据、显示分离的方法来组织代码。主要作用是降低了视图与业务逻辑的双向解耦。
- 模型Model(dao、Service):数据模型,提供要展示的数据,包含数据和行为
- 视图View(JSP):负责模型的展示
- 控制器Controller(Servlet):接收用户请求,委托给Model处理,处理完后返回给View
1.2 回顾Servlet
创建一个Maven项目作为父工程,并创建Maven子项目
- 导入依赖
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.13.1</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.3.3</version>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>4.0.1</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>
</dependencies>
- 添加框架支持
目前项目是一个Maven项目,需要将其变为web项目,在项目名上右键,选择Add Framework Support
,勾选Web Application
- 子项目导入依赖
<dependencies>
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>jsp-api</artifactId>
<version>2.2</version>
<scope>provided</scope>
</dependency>
</dependencies>
- 创建类并继承
HttpServlet
然后重写doGet
和doPost
- 编写
doGet
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 1.获取前端参数
String method = req.getParameter("method");
if (method.equals("add")) {
req.getSession().setAttribute("msg", "执行add方法");
}
if (method.equals("delete")) {
req.getSession().setAttribute("msg", "执行delete方法");
}
// 2.视图转发req或重定向resp
req.getRequestDispatcher("/WEB-INF/jsp/test.jsp").forward(req, resp);
}
- 编写jsp
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
${msg}
</body>
</html>
- 在
web.xml
中注册servlet
<?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">
<servlet>
<servlet-name>hello</servlet-name>
<servlet-class>com.nick.servlet.HelloServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>hello</servlet-name>
<url-pattern>/hello</url-pattern>
</servlet-mapping>
</web-app>
- 写一个页面来调用Servlet
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>表单</title>
</head>
<body>
<form action="/hello" method="post">
<input type="text" name="method">
<input type="submit">
</form>
</body>
</html>
- 配置Tomcat
- 访问
1.3 学习SpringMVC
SpringMVC是Spring Framework的一部分,是基于Java实现的MVC轻量级Web框架。
- 轻量级,简单易学
- 高效,基于请求响应的MVC框架
- 与Spring无缝结合
- 约定大于配置
- 功能强大:RESTful、数据验证、格式化、本地化
- 中心控制器
Spring的Web框架围绕**
DispatcherServlet
**设计,DispatcherServlet
作用是将请求分发到不同的处理器
SpringMVC原理图:
搭建SpringMVC项目
- 新建一个Module,添加Web支持
- 配置
web.xml
,注册DispatcherServlet
<?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">
<!--1. 注册DispatcherServlet-->
<servlet>
<servlet-name>springmvc</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<!--关联一个springmvc的配置文件-->
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:springmvc-servlet.xml</param-value>
</init-param>
<!--启动级别1-->
<load-on-startup>1</load-on-startup>
</servlet>
<!--/匹配所有的请求(不包括.jsp)-->
<!--/*匹配所有的请求(包括.jsp)-->
<servlet-mapping>
<servlet-name>springmvc</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
</web-app>
- 创建DispatcherServlet的配置文件
springmvc-servlet.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: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
http://www.springframework.org/schema/context/spring-context.xsd">
<!--5. 添加处理映射器-->
<bean class="org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping"/>
<!--6. 添加处理适配器-->
<bean class="org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter"/>
<!--7. 添加视图解析器
1. 获取ModelAndView的数据
2. 解析ModelAndView视图名字
3. 拼接视图名字,找到对应的视图
4. 将数据渲染到视图上
-->
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver" id="internalResourceViewResolver">
<!--前缀-->
<property name="prefix" value="/WEB-INF/jsp/"/>
<!--后缀-->
<property name="suffix" value=".jsp"/>
</bean>
<bean id="/hello" class="com.nick.controller.HelloController"/>
</beans>
- 编写Controller
public class HelloController implements Controller {
public ModelAndView handleRequest(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws Exception {
// ModelAndView模型和视图
ModelAndView mv = new ModelAndView();
// 封装对象,放在ModelAndView中
mv.addObject("msg", "HelloSpringMVC");
// 封装要跳转的视图,放到ModelAndView中
mv.setViewName("hello"); // /WEB-INF/hello.jsp
return mv;
}
}
- 编写hello.jsp
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
${msg}
</body>
</html>
-
在
springmvc-servlet.xml
中配置controller的bean -
测试
1.4 SpringMVC执行原理(重要)
-
(1)前端页面访问,会先走到
DispatcherServlet
-
(2,3,4)
DispatcherServlet
会去找处理器映射HandlerMapping
,它会根据URL查找处理器/hello
,并返回给DispatcherServlet
-
(5,6,7,8)
DispatcherServlet
根据/hello
去找处理器适配器,找到具体的HelloController
,该Controller会处理相关业务,并返回一个ModelAndView
,里面包含传递的消息和要跳转的视图 -
(9,10)
DispatcherServlet
拿着ModelAndView
去找视图解析器ViewResolver
,视图解析器会解析视图名称,找对应的视图XXX.jsp
,然后将数据渲染到视图上 -
(11)
DispatcherServlet
根据视图解析器解析视图的结果,调用具体的视图,最终呈现给用户
1.5 使用注解开发SpringMVC
- 新建一个Module,添加web支持
- 在pom中引入相关依赖
- 配置web.xml
- 添加SpringMVC配置文件
这里不需要配置处理器映射和处理器适配器了,为了支持基于注解的IOC,需要设置自动扫描包的功能。
- 自动扫描包:
context:component-scan
- 不处理静态资源:
mvc:default-servlet-handler
HandlerMapping
和HandlerAdapter
注入:mvc:annotation-driven
<!--指定要扫描的包,该包下的注解就会生效-->
<context:component-scan base-package="com.nick.controller"/>
<!--让SpringMVC不处理静态资源 .css .js .html .mp3 .mp4-->
<mvc:default-servlet-handler/>
<!--
支持mvc注解驱动
在Spring中一般采用@RequestMapping注解来完成映射关系
要使@RequestMapping注解生效
必须向上下文中注册DefaultAnnotationHandlerMapping
和一个AnnotationMethodHandlerAdapter实例
这两个实例分别在类级别和方法级别处理
而annotation-driven配置帮助我们自动完成上述两个实例的注入
-->
<mvc:annotation-driven/>
<!-- 视图解析器-->
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver" id="internalResourceViewResolver">
<property name="prefix" value="/WEB-INF/jsp/"/>
<property name="suffix" value=".jsp"/>
</bean>
- 创建Controller
@Controller
public class HelloController {
// 真实访问地址:项目名//hello
@RequestMapping("/hello")
public String Hello(Model model) {
// 封装数据
model.addAttribute("msg", "HelloSpringMVCAnnotation");
// 返回视图的名字,返回结果会被视图解析器处理
return "hello";
}
}
1.6 Controller配置总结
Controller
- 控制器复杂提供访问应用程序的行为,通常通过接口定义或者注解定义两种方式
- 控制器负责解析用户的请求并将其转换为一个模型
- 在SpringMVC中一个控制器类可以包含多个方法
- 在SpringMVC中对于Controller的配置方式有很多种
接口方式
-
编写Controller类
-
去Spring配置文件中注册请求的Bean,
name
对应请求路径,class
对应处理请求的类 -
编写web前端
-
在配置文件中,不用配置映射器和适配器(学习原理使用)
-
返回
ModelAndView
类中通过setName
来设置视图名称 -
缺点:一个控制器只能写一个方法,麻烦
注解方式
@Controller
注解类用于声明Spring类的实例是一个控制器- Spring可以使用扫描机制找到应用中所有基于注解的控制器类,为了保证Spring能找到你的控制器,需要在配置文件中声明组件扫描
<context:component-scan>
- 编写Controller类
- 返回String为视图名称
注解 | 说明 |
---|---|
@Component | 组件(这几个是等价的) |
@Service | Service |
@Controller | Controller |
@Respository | Dao |
1.7 RequestMapping
@RequestMapping
注解用于映射url到控制器类或者一个特定的处理程序方法
- 写在类上时,是父路径
- 也可以写在方法上,是子路径
二、RESTFul风格
2.1 概念
RestFul风格就是一个资源定位及资源操作的风格,不是标准也不是协议,只是一种风格。基于这种风格设计的软件,更有层次,更易于实现缓存机制。
功能
- 资源:互联网所有事物都可以被抽象为资源
- 资源操作:使用
POST
、DELETE
、PUT
、GET
不同方法对资源分别进行添加、删除、修改、查询
传统方式操作资源
传统方式通过不同参数来实现不同效果,方法单一,post
和get
- 查询(GET):
http://127.0.0.1:8080/item/a.action?id=1
- 新增(POST):
http://127.0.0.1:8080/item/b.action
- 更新(POST):
http://127.0.0.1:8080/item/c.action
- 删除(GET或POST):
http://127.0.0.1:8080/item/d.action?id=1
使用RESTFul风格操作资源
RESTFul风格可以通过相同的请求来实现不同的效果,示例就是jira的api使用同一个api,因为方法的不同产生不同的作用
- 查询(GET):
http://127.0.0.1:8080/item/1
- 新增(POST):
http://127.0.0.1:8080/item
- 更新(POST):
http://127.0.0.1:8080/item
- 删除(GET或POST):
http://127.0.0.1:8080/item
2.2 示例
示例
- 传统风格
@Controller
public class TestController {
@RequestMapping("/add")
String testController(int a, int b, Model model) {
int res = a + b;
model.addAttribute("msg", "res=" + res);
return "test";
}
}
- RESTFul风格
在SpringMVC中可以使用**@PathVariable
**注解,让方法参数的值对应绑定到一个URI模板变量上
@RequestMapping("/add2/{a}/{b}")
String testController2(@PathVariable int a, @PathVariable int b, Model model) {
int res = a + b;
model.addAttribute("msg", "res=" + res);
return "test";
}
优点:这种RESTFul风格不会将参数名暴露给用户,更安全
三、重定向与转发
- 方式一:使用ServletAPI
重定向
- 方法:
sendRedirect
- 类:
HttpServletResponse
转发:
- 方法:
getRequestDispatcher
- 类:
HttpServletResponse
- 方式二:使用SpringMVC方式,修改
Controller
的返回值
有视图解析器的时候,直接返回"xxx"
,视图解析器会拼接前缀和后缀,默认是转发。
使用重定向或者转发的方式,直接返回路径加后缀,因此不需要视图解析器了。
重定向
return "redirect:/xxx.jsp"
转发
return "forward:/xxx.jsp"
return "/xxx.jsp"
四、接收请求参数及数据回显
4.1 接收请求参数
- 提交的与名称和处理方法参数名一致,可以直接处理
- 提交的域名称和处理方法的参数名不一致
- 提交一个对象
- 会自动匹配对象中的字段名,如果一致则可以直接使用对象来接收
4.2 数据回显
- 通过
ModelAndView
- 通过
ModelMap
- 通过
Model
区别
Model
:精简版,大部分情况下直接使用Model
ModelMap
:继承LinkedHashMap
,所以有其所有功能ModelAndView
:可以在存储数据的同时,进行设置返回逻辑视图
4.3 解决乱码问题
使用过滤器来解决乱码
使用自定义过滤器
- 实现
Filter
接口
- 进行配置
使用SpringMVC过滤器
org.springframework.web.filter.CharacterEncodingFilter
CharacterEncodingFilter
类本质还是实现filter
,但是其做了很多其他工作
五、JSON讲解
5.1 什么是JSON
- JSON(JavaScript Object Notation,JS对象标记)是一种轻量级的数据交换格式,目前使用特别广泛
- 采用完全独立的编程语言文本格式来存储和表示数据
- 简洁清晰的层次结构
在JavaScript中,一切皆对象,因此JavaScript支持的类型都可以通过JSON来表示,例如字符串、数字、对象、数组等
- 对象表示为键值对,数据由逗号分隔
- 花括号保存对象
- 方括号保存数组
5.2 Jackson使用
5.2.1 基础使用
- 导包
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.13.1</version>
</dependency>
- 编写Controller
@Controller
public class JsonTestController {
/**
* @ResponseBody 注解添加后,方法就不会走视图解析器,会直接返回一个字符串
*/
@RequestMapping("t1")
@ResponseBody
public String test1() throws JsonProcessingException {
User user = new User("nick", 26, "男");
ObjectMapper mapper = new ObjectMapper();
String str = mapper.writeValueAsString(user);
return str;
}
}
说明:
- 如果使用
@Controller
会走视图解析器,如果不想返回视图,搭配@ResponseBody
使用- 或者不使用
@Controller
直接使用@RestController
,效果一样
- 效果
5.2.2 JSON转换乱码
虽然配置了SpringMVC的过滤器,但是这里转JSON的时候还是会出现中文乱码,解决方案如下:
- 方案一:原生态解决方式,在
@RequestMapping
中配置produces
@RequestMapping(value = "t1", produces = "application/json;charset=UTF-8")
- 方案二:配置
<mvc:annotation-driven>
<mvc:annotation-driven>
<mvc:message-converters>
<bean class="org.springframework.http.converter.StringHttpMessageConverter">
<constructor-arg value="UTF-8"/>
</bean>
<bean class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter">
<property name="objectMapper">
<bean class="org.springframework.http.converter.json.Jackson2ObjectMapperFactoryBean">
<property name="failOnEmptyBeans" value="false"/>
</bean>
</property>
</bean>
</mvc:message-converters>
</mvc:annotation-driven>
在其中配置一个mvc:message-converters
,需要配置两个bean,分别是StringHttpMessageConverter
和MappingJackson2HttpMessageConverter
,其中第一个类由于没有set方法,因此要使用构造器注入。
5.2.3 Date类型转换JSON
- 通常可以使用format来先将Date类型转换成带格式的String,然后给
ObjectMapper
- 其实
ObjectMapper
本身就可以对时间格式进行设置,具体如下
@RequestMapping(value = "t2")
@ResponseBody
public String test2() throws JsonProcessingException {
Date date = new Date();
ObjectMapper mapper = new ObjectMapper();
// ObjectMapper可以配置关闭将日期转换为时间戳
mapper.configure(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS, false);
// ObjectMapper可以配置日期格式
mapper.setDateFormat(new SimpleDateFormat("yyyy-MM-dd hh:mm:ss"));
String str = mapper.writeValueAsString(date);
return str;
}
六、整合Mybatis
6.1 相关依赖整理
6.1.1 数据库相关
- 数据库驱动
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.27</version>
</dependency>
- 数据库连接池(jdbc、c3p0、D)
<dependency>
<groupId>com.mchange</groupId>
<artifactId>c3p0</artifactId>
<version>0.9.5.5</version>
</dependency>
6.1.2 网络相关
- Servlet
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>4.0.1</version>
<scope>provided</scope>
</dependency>
- JSP
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>javax.servlet.jsp-api</artifactId>
<version>2.3.3</version>
<scope>provided</scope>
</dependency>
- jstl
<dependency>
<groupId>javax.servlet.jsp.jstl</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>
6.1.3 Mybatis相关
- mybatis
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.5.9</version>
</dependency>
- mybatis-spring
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis-spring</artifactId>
<version>2.0.6</version>
</dependency>
6.1.4 SpringMVC相关
- springmvc
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.3.14</version>
</dependency>
- JDBC
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>5.3.14</version>
</dependency>
6.2 静态资源导出问题处理
<build>
<resources>
<resource>
<directory>src/main/java</directory>
<includes>
<include>**/*.properties</include>
<include>**/*.xml</include>
</includes>
<filtering>false</filtering>
</resource>
<resource>
<directory>src/main/resources</directory>
<includes>
<include>**/*.properties</include>
<include>**/*.xml</include>
</includes>
<filtering>false</filtering>
</resource>
</resources>
</build>
6.3 Mybatis准备工作
6.3.1 database.properties
jdbc.dirver = com.mysql.cj.jdbc.Driver
jdbc.url = jdbc:mysql://localhost:3306/ssmbuild?useSSL=true&useUnicode=true&characterEncoding=utf8&serverTimeZone=GMT
jdbc.user = root
jdbc.password = wang2995
6.3.2 mybatis-config.xml
-
配置数据源(交给Spring去做)
-
别名
-
配置Mapper
<?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>
<typeAliases>
<package name="com.nick.pojo"/>
</typeAliases>
</configuration>
6.4 Mapper
6.4.1 dao层编写BookMapper接口
public interface BookMapper {
/**
* 增加一本书
* @param books
* @return
*/
int addBook(Books books);
/**
* 删除一本书
* @param id
* @return
*/
int deleteBookById(int id);
/**
* 修改一本书
* @param books
* @return
*/
int updateBook(Books books);
/**
* 查询一本书
* @param id
* @return
*/
Books queryBookById(int id);
/**
* 查询所有书
* @return
*/
List<Books> queryAllBooks();
}
6.4.2 创建BookMapper.xml
在Mapper
中namespace
对应BookMapper
接口
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.nick.dao.BookMapper">
<insert id="addBook" parameterType="com.nick.pojo.Books">
insert into books(bookName, bookCount, detail)
values(#{bookName}, #{bookCount}, #{detail})
</insert>
<update id="updateBook" parameterType="com.nick.pojo.Books">
update books
set bookName=#{bookName}, bookCount=#{bookCount}, detail=#{detail}
where bookID = #{bookID}
</update>
<delete id="deleteBookById" parameterType="java.lang.Integer">
delete from books
where bookID = #{bookID}
</delete>
<select id="queryBookById" resultType="com.nick.pojo.Books" parameterType="java.lang.Integer">
select *
from books
where bookID = #{bookID}
</select>
<select id="queryAllBooks" resultType="com.nick.pojo.Books">
select * from books
</select>
</mapper>
6.4.3 将BookMapper.xml绑定到mybatis-config.xml中
<configuration>
<typeAliases>
<package name="com.nick.pojo"/>
</typeAliases>
<mappers>
<mapper class="com.nick.dao.BookMapper"/>
</mappers>
</configuration>
6.5 Service
6.5.1 BookService接口
实现和Dao层的接口一致
6.5.2 BookServiceImpl实现
业务层调用dao层即可
七、整合Spring层
7.1 编写spring-dao.xml
- 关联数据库配置文件
- 连接池
- SQLSessionFactory
<?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
http://www.springframework.org/schema/context/spring-context-4.2.xsd">
<!--1. 关联数据库配置文件-->
<context:property-placeholder location="classpath:database.properties"/>
<!--2. 连接池
dbcp(半自动化,手动连接)
c3p0(自动化操作,自动化加载配置文件,且自动设置到对象中)
druid
hikari-->
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
<property name="driverClass" value="${jdbc.dirver}"/>
<property name="jdbcUrl" value="${jdbc.url}"/>
<property name="user" value="${jdbc.user}"/>
<property name="password" value="${jdbc.password}"/>
<!--c3p0私有属性-->
<property name="maxPoolSize" value="30"/>
<property name="minPoolSize" value="10"/>
<property name="initialPoolSize" value="10"/>
<!--关闭连接后不自动commit-->
<property name="autoCommitOnClose" value="false"/>
<!--获取连接超时时间-->
<property name="checkoutTimeout" value="10000"/>
<!--当获取连接失败重试次数-->
<property name="acquireRetryAttempts" value="2"/>
</bean>
<!--3. sqlSessionFactory-->
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource"/>
<property name="configLocation" value="classpath:mybatis-config.xml"/>
</bean>
<!--4. 配置dao接口扫描包,通过反射动态实现dao接口自动注入到Spring容器中-->
<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<!--注入sqlSessionFactory-->
<property name="sqlSessionFactoryBeanName" value="sqlSessionFactory"/>
<!--扫描要扫描的dao包-->
<property name="basePackage" value="com.nick.dao"/>
</bean>
</beans>
7.2 spring-service.xml
- 扫描Service下的包
- 将所有业务类注入到Spring中
- 声明式事务
<?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
http://www.springframework.org/schema/context/spring-context-4.2.xsd">
<!--1. 扫描Service下的包-->
<context:component-scan base-package="com.nick.service"/>
<!--2. 将所有业务层的类注入到Spring-->
<bean id="BookServiceImpl" class="com.nick.service.BookServiceImpl">
<property name="bookMapper" ref="bookMapper"/>
</bean>
<!--3. 声明式事物-->
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<!--注入数据源-->
<property name="dataSource" ref="dataSource"/>
</bean>
</beans>
八、整合SpringMVC层
8.1 web.xml
- DispatcherServlet
- 乱码过滤
<?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">
<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:applicationContext.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>
<filter>
<filter-name>encodeing</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>encodeing</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
</web-app>
8.2 spring-mvc.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: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">
<context:component-scan base-package="com.nick.controller"/>
<mvc:default-servlet-handler/>
<mvc:annotation-driven/>
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver" id="internalResourceViewResolver">
<property name="prefix" value="/jsp/"/>
<property name="suffix" value=".jsp"/>
</bean>
</beans>
九、整合说明
9.1 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"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<import resource="classpath:spring-dao.xml"/>
<import resource="classpath:spring-service.xml"/>
<import resource="classpath:spring-mvc.xml"/>
</beans>
9.2 spring-dao.xml
- 关联数据库配置文件(
database.properties
) - 连接池(
c3p0
) sqlSessionFactory
(数据源、配置文件路径mybatis-config.xml
)- 别名
mapper
- 配置dao接口扫描包
9.3 spring-service.xml
- 扫描Service包
- 将所有业务层类注入Spring(
BookServiceImpl
) - 声明式事务(
DataSourceTransactionManager
中注入数据源)
9.4 spring-mvc.xml
-
注解驱动
-
静态资源过滤
-
扫描包
-
视图解析器
9.5 编写Controller
@Controller
@RequestMapping("/book")
public class MybatisController {
@Autowired
@Qualifier("BookServiceImpl")
private BookService bookService;
@RequestMapping("/allBook")
public String queryAll(Model model) {
List<Books> books = bookService.queryAllBooks();
model.addAttribute("list", books);
return "allBook";
}
}
十、拦截器
10.1 概述
SpringMVC的处理器拦截器类似于Servlet中过滤器Filter,用于对处理器进行预处理和后处理。
拦截器与过滤器的区别:拦截器是AOP思想的具体应用
- 过滤器
- servlet规范中一部分,任何java web工程都可以使用
- 在
url-pattern
中配置/*
之后,可以对所有要访问资源进行拦截
- 拦截器
- 拦截器是SpringMVC框架自己的,只有使用了SpringMVC框架的工程才能使用
- 拦截器只会拦截访问的控制器的方法,如果访问的是
jsp/html/css/image/js
是不会拦截的
10.2 自定义拦截器
要想自定义拦截器,必须实现
HandlerInterceptor
接口
public class MyInterceptor implements HandlerInterceptor {
/**
*
* @param request
* @param response
* @param handler
* @return 为true就放行,执行下一个拦截器。如果return false
* 就会将请求拦截,controller中的方法不会被执行
* @throws Exception
*/
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
System.out.println("==============处理前==============");
return true;
}
/* 一般写拦截日志 */
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
System.out.println("==============处理后==============");
}
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
System.out.println("==============清理==============");
}
}
配置拦截器
<!--拦截器-->
<mvc:interceptors>
<mvc:interceptor>
<!--包括这个请求以及下面的所有请求-->
<mvc:mapping path="/**"/>
<bean class="com.nick.config.MyInterceptor" id="myInterceptor"/>
</mvc:interceptor>
</mvc:interceptors>