Mybatis:优化了dao层,降低了java与dao层的耦合
Spring :优化了service层,降低了java与service层的耦合
SpringMVC :优化了servlet层,降低了java与servlet层的耦合
SpringMVC(主流MVC框架):是Spring框架的一部分(子框架),是实现对Servlet技术进行封装。
1.SpringMVC运行原理(执行过程)
2.需求:用户提交一个请求,服务端处理器接收到请求后,给出一条信息,在相应页面中显示该条信息
3.开发步骤
3.1导入jar包
3.2配置web.xml,注册SpringMVC前端控制器(中央调度器)
3.3编写SpringMVC后端控制器
3.4编写springmvc配置文件,注册后端控制器(注意id写法格式)
配置文件的约束:
<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: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/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.0.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">
beans>
3.5编写跳转资源页面
package com.spring.controller;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.mvc.Controller;
public class MyController implements Controller {
@Override
public ModelAndView handleRequest(javax.servlet.http.HttpServletRequest httpServletRequest, javax.servlet.http.HttpServletResponse httpServletResponse) throws Exception {
//创建视图模型对象
ModelAndView m = new ModelAndView();
m.addObject("name","张三");//往视图模型中加入流转数据
m.setViewName("index.jsp");//设置要跳转的页面
return m;
}
}
注解式开发:
<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: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/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.0.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">
<bean id="/myController" class="com.spring.controller.MyController">bean>
beans>
4.web.xml中urlpattern配置问题
<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>dispatcherServletservlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServletservlet-class>
servlet>
<servlet-mapping>
<servlet-name>dispatcherServletservlet-name>
<url-pattern>/url-pattern>
servlet-mapping>
web-app>
4.1配置静态资源放行
<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: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/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.0.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">
<bean id="/myController" class="com.spring.controller.MyController">bean>
<mvc:resources mapping="/image/**" location="/image/"/>
beans>
1.搭建环境
1.1 后端控制器无需实现接口,添加相应注解
1.2 springmvc配置文件无需注册controller
1.3 springmvc配置文件中添加组件扫描器、注解驱动
在配置文件中加上下面:
<context:component-scan base-package="spring.control">context:component-scan>
<mvc:annotation-driven>mvc:annotation-driven>
2.涉及常用注解
@Controller、@Scope 加载类上
@RequestMapping(类体上【命名空间】、方法上)、
类上的@RequestMapping :限定范围的作用,限定在浏览器上访问的路径
方法上的@RequestMapping :请求路径
在类名@Controller下一行加:@Scope(“prototype”) //表示每次请求都会创建新的实例,去掉就不会了
实例
package com.spring.controller;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
@Controller //加这个注解等同于: ,同时实现了接口
@Scope(value = "prototype") //原型模式
@RequestMapping("/user") //类上面加了限定路径名,访问的时候/user/show
public class MyController{
@RequestMapping("/show") //在浏览器上请求处理的控制器方法,限定路径的访问名
public ModelAndView show(){
ModelAndView m = new ModelAndView(); //用视图模型对像作为数据载体
m.addObject("name","曹操");
m.setViewName("/index.jsp");
return m;
}
@RequestMapping("/show2")
public String show2(HttpServletRequest req, HttpServletResponse resp){
//内置对象,可以直接作为形式参数使用
req.setAttribute("name","刘备");//req域作为数据的流转载体
return "/index.jsp";//页面的跳转,如果在类上加了父路径名,这里在页面前加一个/表示访问起始从根路径开始
}
}
4.处理器方法常用的内置参数(五类)
4.1 HttpServletRequest
4.2 HttpServletResponse
4.3 HttpSession
4.4 用于承载数据的Model、Map
4.5 请求中所携带的请求参数
@RequestMapping("/show2")
public String show2(HttpServletRequest req, HttpServletResponse resp){
//内置对象,可以直接作为形式参数使用
req.setAttribute("name","刘备");//req域作为数据的流转载体
return "/index.jsp";//页面的跳转,如果在类上加了父路径名,这里在页面前加一个/表示访问起始从根路径开始
}
@RequestMapping("/show3")
public String show3(HttpSession session, Map<String,String> map, Model model){
session.setAttribute("name","赵飞燕"); //session域作为数据载体
//使用Map作为数据载体
map.put("city","长沙");
map.put("province","湖南");
model.addAttribute("phone","136789898798");
return "/index.jsp";
}
5.接收请求参数
5.1 逐个接收 (涉及注解@RequestParam)
5.2 以对象形式整体接收
5.3 域属性参数的接收
5.4 数组或集合参数的接收
5.5 restfull风格,传参(涉及注解@ PathVariable)
5.6 接收json字符串(涉及注解@ResponseBody)
6.获取请求头中参数(涉及注解@RequestHeader)
package com.spring.controller;
import com.spring.pojo.User;
import org.springframework.format.annotation.DateTimeFormat;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.util.Date;
@Controller
public class LoginController {
@RequestMapping("/login")
public String login(HttpServletRequest req, HttpServletResponse resp){
String uname = req.getParameter("uname");
String pwd = req.getParameter("pwd");
System.out.println(uname);
System.out.println(pwd);
return "success.jsp";
}
//逐个接收提交的数据
@RequestMapping("/login2")
public String login2(String uname,String pwd,String[]favor,String birthday){
//参数名字与表单中的name里面的值一致即可
System.out.println(uname);
System.out.println(pwd);
for(String str:favor){
System.out.println(str);
}
System.out.println(birthday);
return "success.jsp";
}
//逐个接收提交的数据
@RequestMapping("/login3")
public String login3(String uname, String pwd, String[]favor,@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") Date birthday){
//@DateTimeFormat可以把提交字符串转成Date对象
System.out.println(uname);
System.out.println(pwd);
for(String str:favor){
System.out.println(str);
}
System.out.println(birthday);
return "success.jsp";
}
@RequestMapping("/login4")
public String login4(User user, HttpSession session){
session.setAttribute("user",user);
return "success.jsp";
}
@RequestMapping("/login5/{username}/{password}") //{username}表示接收uri携带的数据,并取名为username
public String login5(@PathVariable String username,@PathVariable String password){
System.out.println(username);
System.out.println(password);
return "success.jsp";
}
@RequestMapping("/login6")
@ResponseBody() //加了这个注解之后返回的return变成了一个数据ResponseBody(响应体),而不是页面跳转
public String login6(String name,String age){
System.out.println(name);
System.out.println(age);
String json = "{'name':'"+name+"','age':'"+age+"'}";
System.out.println(json);
// return "success.jsp";//默认情况下return是跳转页面
return json;
}
}
解决jsp中路径的问题
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
%>
<html>
<head>
<base href="<%=basePath%>">
<title>Titletitle>
head>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";//basePath是当前项目的根目录
%>
<html>
<head>
<base href="<%=basePath%>"> <%--当前jsp下所有的路径的起点是当前工程的根目录--%>
<title>Titletitle>
head>
<body>
Success!<br/>
<%= basePath%>
${user.uname}--
${user.pwd}<br/>
<img src="image/9.jpg" width="80px" alt="图片找不到...">
body>
html>
6.1解决中文乱码问题:
CharacterEncodingFilter
<filter>
<filter-name>characterEncodingFilterfilter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilterfilter-class>
<init-param>
<param-name>encodingparam-name>
<param-value>utf-8param-value>
init-param>
filter>
<filter-mapping>
<filter-name>characterEncodingFilterfilter-name>
<url-pattern>/*url-pattern>
filter-mapping>
设置响应编码
@RequestMapping(value = "/login",produces = "text/html;charset=utf-8")
7.处理器方法的返回值
7.1 ModelAndView
7.2 String
7.3 void (使用场景:方法参数为HttpServletRequest和HttpServletResponse时获取用户提交数据时使用)
7.4 Object(涉及注解@ResponseBody ,导入jackson相关的包)
package com.spring.controller;
import com.spring.pojo.User;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@Controller
public class TestController {
@RequestMapping("/getMsg")
public void getMsg(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// req.getRequestDispatcher("success.jsp").forward(req,resp); //请求转发
resp.sendRedirect("success.jsp");
}
@RequestMapping("/getObj")
@ResponseBody
public Object getObj(){
User user= new User("赵飞燕","123456");
return user;//需要依赖user返回的过程之中会转成json数据
}
}
8.请求转发与重定向
package com.spring.controller;
import com.spring.pojo.User;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@Controller
public class TestController2 {
@RequestMapping("/showPage")
public String showPage(){
return "forward:success.jsp"; //默认就是请求转发,forward:默认情况下可以省略
}
@RequestMapping("/showPage2")
public String showPage2(){
return "redirect:success.jsp"; //重定向,redirect:不能省略
}
}
为了提高了项目访问的安全性及统一管理,资源放在WEB-INF
原理:
静态及jsp资源放在WEB-INF下,客户端不能直接访问,服务端才可以访问到,也就是说别人不能够串改你的代码。
为了方便让Spring映射:就是配置文件上会带有对静态资源的配置信息
如果想在页面中直接访问其中的文件,必须通过视图解析器对要访问的文件进行相应映射才能访问。
__ 映射文件:__
package com.spring.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class PageController {
@RequestMapping("/showPage")
public String showPage(){
return "WEB-INF/jsp/abc.jsp";
}
//动态实现控制器跳转到jsp文件
@RequestMapping("/{page}")
public String getPage(@PathVariable String page){
// return "WEB-INF/jsp/"+page+".jsp";
return page;
}
}
视图解析器(前缀、后缀)
配置html的解析器需要先引入freemarker-2.3.28.jar
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/jsp/">property>
<property name="suffix" value=".jsp">property>
<property name="order" value="1">property>
bean>
<bean class="org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer">
<property name="templateLoaderPath">
<value>/WEB-INF/html/value>
property>
<property name="defaultEncoding">
<value>utf-8value>
property>
bean>
<bean class="org.springframework.web.servlet.view.freemarker.FreeMarkerViewResolver">
<property name="viewClass" value="org.springframework.web.servlet.view.freemarker.FreeMarkerView"/>
<property name="contentType" value="text/html; charset=utf-8"/>
<property name="suffix" value=".html" />
<property name="order" value="0"/>
bean>
自定义SpringMVC的配置文件路径和文件名
在web.xml的中央调度器中配置
<servlet>
<servlet-name>dispatcherServletservlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServletservlet-class>
<init-param>
<param-name>contextConfigLocationparam-name>
<param-value>classpath:springmvc.xmlparam-value>
init-param>
servlet>
<servlet-mapping>
<servlet-name>dispatcherServletservlet-name>
<url-pattern>/url-pattern>
servlet-mapping>
在Spring整体框架的核心概念中,容器是核心思想,就是用来管理Bean的整个生命周期的,而在一个项目中,容器不一定只有一个,Spring中可以包括多个容器,而且容器有上下层关系,目前最常见的一种场景就是在一个项目中引入Spring和SpringMVC这两个框架,那么它其实就是两个容器,Spring是父容器,SpringMVC是其子容器,并且在Spring父容器中注册的Bean对于SpringMVC容器中是可见的,而在SpringMVC容器中注册的Bean对于Spring父容器中是不可见的,也就是子容器可以看见父容器中的注册的Bean,反之就不行。