Gitee仓库:狂神-SpringMVC: 学习狂神的课程,练习项目 - Gitee.com
1、什么是MVC
最经典的MVC就是JSP + Servlet + javabean的模式。
2、model时代
Model1时代
Model2时代
Model2把一个项目分成三部分,包括 视图、控制、模型
Model2这样不仅提高的代码的复用率与项目的扩展性,且大大降低了项目的维护成本。
Model1模式的实现比较简单,适用于快速开发小规模项目,Model中JSP页面身兼View和Controller两种角色,将控制逻辑和表现逻辑混杂在一起,从而导致代码的重用性非常低,增加了应用的扩展性和维护的难度,Model2消除了Model1的缺点。
MVC框架要做哪些事情?
常见的服务器端MVC框架有
Struts、Spring MVC、 ASP.NET MVC、 Zend Framework、JSF;常见前端MVC框架:vue、angularjs、react、backbone;由MVC演化出了另外一些模式,如:MVP、MVVM等等……
面试:你的项目架构,是设计好的,还是演进的
官方网址
1 、什么是 Spring MVC?
Spring MVC是Spring Framework的一部分,是基于Java实现MVC的轻量级Web框架。
分析源码,看到DispatcherServlet继承了HttpServlet。
内部有对request、response的前置处理,后置处理。
2、为什么要学习Spring MVC?
Spring MVC的特点:
最重要一点还是用的人多,使用得公司多,接触得项目基本都用到了。
Spring的web框架围绕DispatcherServlet[调度Servlet]设计。
DispatcherServlet的作用是将请求分发到不同的处理器。从Spring 2.5开始,使用Java 5或者以上版本的用户可以采用基于注解形式进行开发,十分简洁;
3、DispatcherServlet
Spring MVC框架像许多其它MVC框架一样,以请求为驱动,围绕一个中心Servlet分派请求及提供其它功能,DispatcherServlet是一个实际的Servlet(它继承自HttpServlet基类)。
SpringMVC的原理如下图所示:
4、SpringMVC执行原理
注: 图为SpringMVC的一个较完整的流程图,实线表示SpringMVC框架提供的技术,不需要开发者实现,虚线表示需要开发者实现。
简要分析执行流程
首先在父项目导入依赖
org.springframework
spring-webmvc
5.3.10
javax.servlet
javax.servlet-api
3.1.0
javax.servlet.jsp
javax.servlet.jsp-api
2.3.3
javax.servlet.jsp.jstl
jstl-api
1.2
org.projectlombok
lombok
1.18.20
junit
junit
4.13
src/main/java
**/*.properties
**/*.xml
false
src/main/resources
**/*.properties
**/*.xml
false
1、配置版
首先创建maven项目,然后添加项目支持
选择WebApp的4.0版本
项目结构
配置Project Structure,否则会识别不出web项目结构,报500can not find springmvc-servlet.xml
报错页面
web.xml
springmvc1
org.springframework.web.servlet.DispatcherServlet
contextConfigLocation
classpath:springmvc1-servlet.xml
1
springmvc1
/
springMVC1-servlet.xml
HelloController.java
public class HelloController implements Controller {
@Override
public ModelAndView handleRequest(HttpServletRequest request, HttpServletResponse response) throws Exception {
// 创建返回对象
ModelAndView modelAndView = new ModelAndView();
// 放入参数
modelAndView.addObject("msg", "hello Controller");
// 设置跳转的页面 /WEB-INF/jsp/hello.jsp
modelAndView.setViewName("hello");
return modelAndView;
}
}
启动项目测试
2、注解版
只有列出来的2个文件和配置版有不同。
项目结构
springmvc2-servlet.xml
HelloController.java
@Controller
public class HelloController {
@RequestMapping("/hello")
public String hello(Model model) {
model.addAttribute("msg", "hello Controller");
return "hello";
}
启动项目测试
小结
实现步骤其实非常的简单:
1、什么是Restful
Restful就是一个资源定位及资源操作的风格。不是标准也不是协议,只是一种风格。基于这个风格设计的软件可以更简洁,更有层次,更易于实现缓存等机制。
2、RestFul的功能
传统方式操作资源 :
通过不同的参数来实现不同的效果!方法单一,post 和 get
http://127.0.0.1/item/queryItem.action?id=1 查询,GET
http://127.0.0.1/item/saveItem.action 新增,POST
http://127.0.0.1/item/updateItem.action 更新,POST
http://127.0.0.1/item/deleteItem.action?id=1 删除,GET或POST
使用RESTful操作资源 :
可以通过不同的请求方式来实现不同的效果!如下:请求地址一样,但是功能可以不同!
http://127.0.0.1/item/1 查询,GET
http://127.0.0.1/item 新增,POST
http://127.0.0.1/item 更新,PUT
http://127.0.0.1/item/1 删除,DELETE
编写项目测试
RestfulController.java
// @PathVariable 注解,让方法参数的值对应绑定到一个URI模板变量上。PathVariable:路径变量
@RequestMapping(value = "/restful1/{a}/{b}")
public String restful1(@PathVariable int a, @PathVariable int b, Model model) {
int result = a + b;
//Spring MVC会自动实例化一个Model对象用于向视图中传值
model.addAttribute("msg", "result = " + result);
//返回视图位置
return "hello";
}
// 使用method属性指定请求类型
@RequestMapping(value = "/restful2/{a}/{b}", method = RequestMethod.POST)
public String restful2(@PathVariable int a, @PathVariable int b, Model model) {
int result = a + b;
//Spring MVC会自动实例化一个Model对象用于向视图中传值
model.addAttribute("msg", "result = " + result);
//返回视图位置
return "hello";
}
思考:使用路径变量的好处?
方法级别的注解变体有如下几个:组合注解
@GetMapping = @RequestMapping(method =RequestMethod.GET)
@PostMapping
@PutMapping
@DeleteMapping
@PatchMapping
servlet本身具有转发和重定向,springMVC对他做了封装
1、通过SpringMVC来实现转发和重定向 - 无需视图解析器
视图解析器,默认就是转发,所以要把他注释掉
@RequestMapping("/redirect1")
public String redirect1(HttpServletRequest request, HttpServletResponse response) {
HttpSession session = request.getSession();
System.out.println(session.getId());
// return "hello";
// 转发方式一
// return "/WEB-INF/jsp/hello.jsp";
// 转发方式二
return "forward:/WEB-INF/jsp/hello.jsp";
// 重定向
// return "redirect:/index.jsp";
}
2、通过SpringMVC来实现转发和重定向 - 有视图解析器
@RequestMapping("/redirect2")
public String redirect2(Model model) {
model.addAttribute("msg", "hello Controller");
// return "hello";
// 重定向
return "redirect:/index.jsp";
}
1、处理提交数据
提交的域名称和处理方法的参数名一致
// http://localhost:8080/springmvc3_restful/user/test1?name=Daniel
@RequestMapping("/test1")
public String test1(Model model, String name) {
// 1.接收前端传过来的数据
System.out.println("前端传过来的数据" + name);
// 2.将返回的结果传递给前端
model.addAttribute("msg", name);
// 3.视图跳转
return "hello";
}
提交的域名称和处理方法的参数名不一致
// http://localhost:8080/springmvc3_restful/user/test2?username=Daniel
@RequestMapping("/test2")
public String test2(Model model, @RequestParam("username") String name) {
// 1.接收前端传过来的数据
System.out.println("前端传过来的数据" + name);
// 2.将返回的结果传递给前端
model.addAttribute("msg", name);
// 3.视图跳转
return "hello";
}
提交的是一个对象
// http://localhost:8080/springmvc3_restful/user/test3?name=Daniel&age=18
@RequestMapping("/test3")
public String test3(Model model, User user) {
// 1.接收前端传过来的数据
System.out.println("前端传过来的数据" + user.toString());
// 2.将返回的结果传递给前端
model.addAttribute("msg", user.toString());
// 3.视图跳转
return "hello";
}
启动项目运行
2、数据显示到前端
第一种 : 通过ModelAndView
@RequestMapping("/t1")
public ModelAndView test1(ModelAndView model) {
model.addObject("msg", "Jenny311");
model.setViewName("hello");
return model;
}
第二种 : 通过ModelMap
@RequestMapping("/t2")
public String test2(ModelMap model) {
model.addAttribute("msg", "Jenny311");
return "hello";
}
第三种 : 通过Model
@RequestMapping("/t3")
public String test3(Model model) {
model.addAttribute("msg", "Jenny311");
return "hello";
}
总结对比:
Model 只有寥寥几个方法只适合用于储存数据,简化了新手对于Model对象的操作和理解;
ModelMap 继承了 LinkedMap ,除了实现了自身的一些方法,同样的继承 LinkedMap 的方法和特性;
ModelAndView 可以在储存数据的同时,可以进行设置返回的逻辑视图,进行控制展示层的跳转。
1、什么是JSON
在 JavaScript 语言中,一切都是对象。因此,任何JavaScript 支持的类型都可以通过 JSON 来表示,例如字符串、数字、对象、数组等。看看他的要求和语法格式:
jsonTest.html
Title
启动项目
2、Jackson
导入依赖
com.fasterxml.jackson.core
jackson-databind
2.13.3
项目结构
web.xml
springmvc4
org.springframework.web.servlet.DispatcherServlet
contextConfigLocation
classpath:springmvc4-json.xml
1
springmvc4
/
encoding
org.springframework.web.filter.CharacterEncodingFilter
encoding
utf-8
encoding
/
JacksonController.java
package com.kuang.controller;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.kuang.pojo.User;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
// 相当于@Controller + @ResponseBody
@RestController
public class JacksonController {
// 不走视图解析器,直接返回(字符串)
@ResponseBody
// 防止乱码
@RequestMapping(value = "/jackson1", produces = "application/json;charset=utf-8")
public String jackson1() throws JsonProcessingException {
ObjectMapper objectMapper = new ObjectMapper();
User user = new User(12, "安卓", "男");
return objectMapper.writeValueAsString(user);
}
@RequestMapping("/jackson2")
public String jackson2() throws JsonProcessingException {
ObjectMapper objectMapper = new ObjectMapper();
// 测试集合的输出
List userList = new ArrayList<>();
User user = new User(12, "安卓", "男");
User user2 = new User(12, "安卓", "男");
userList.add( user);
userList.add( user2);
return objectMapper.writeValueAsString(userList);
}
@RequestMapping("/jackson3")
public String jackson3() throws JsonProcessingException {
ObjectMapper objectMapper = new ObjectMapper();
// 测试集合的输出
Date date = new Date();
return objectMapper.writeValueAsString(date);
}
}
启动项目测试
输出集合
输出日期格式
Jackson 默认是会把时间转成timestamps(时间戳)形式
3、Fastjson
fastjson.jar是 阿里 开发的一款专门用于Java开发的包,可以方便的实现json对象与JavaBean对象的转换,实现JavaBean对象与json字符串的转换,实现json对象与json字符串的转换。实现json的转换方法很多,最后的实现结果都是一样的。
导入依赖
com.alibaba
fastjson
2.0.10
fastjson 三个主要的类:
(1) JSONObject 代表 json 对象
(2) JSONArray 代表 json 对象数组
(3) JSON类源码分析与使用
仔细观察这些方法,主要是实现json对象,json对象数组,javabean对象,json字符串之间的相互转化。
FastJsonController.java
package com.kuang.controller;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.kuang.pojo.User;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.ArrayList;
import java.util.List;
@RestController
public class FastjsonController {
@RequestMapping("/fastJson")
public String fastJson() {
//创建对象
User user1 = new User("安卓1", 12, "男1");
User user2 = new User("安卓2", 12, "男2");
User user3 = new User("安卓3", 12, "男3");
User user4 = new User("安卓4", 12, "男4");
List list = new ArrayList<>();
list.add(user1);
list.add(user2);
list.add(user3);
list.add(user4);
String fast = JSON.toJSONString(list);
System.out.println("*******Java对象 转 JSON字符串*******");
String str1 = JSON.toJSONString(list);
System.out.println("JSON.toJSONString(list)==>" + str1);
String str2 = JSON.toJSONString(user1);
System.out.println("JSON.toJSONString(user1)==>" + str2);
System.out.println("\n****** JSON字符串 转 Java对象*******");
User jp_user1 = JSON.parseObject(str2, User.class);
System.out.println("JSON.parseObject(str2,User.class)==>" + jp_user1);
System.out.println("\n****** Java对象 转 JSON对象 ******");
JSONObject jsonObject1 = (JSONObject) JSON.toJSON(user2);
System.out.println("(JSONObject) JSON.toJSON(user2)==>" + jsonObject1.getString("name"));
System.out.println("\n****** JSON对象 转 Java对象 ******");
User to_java_user = JSON.toJavaObject(jsonObject1, User.class);
System.out.println("JSON.toJavaObject(jsonObject1, User.class)==>" + to_java_user);
return fast;
}
}
启动项目
1、什么是Ajax
同步与异步区别
局部更新
资源跳转方式: 请求转发 重定向 (整体更新)
应用场景:
JS原生的异步无刷新方法
项目结构
normalTest.html
iframe测试体验无数新页面
请输入地址:
启动项目测试
2、Ajax的实现方式
JS的ajax
缺点
JQuery的ajax
3、JQuery的Ajax的介绍
jquery是一个优秀的js框架,自然对js原生的ajax进行了封装,封装后的ajax的操作方法更简洁,功能更强大,与ajax操作相关的jquery方法有如下几种,但开发中经常使用的有三种:
其中,参数说明如下:
url : 请求路径。 向某个路径发送请求。
data : 发送请求时的参数列表。
写法格式 : {“属性名1”:”属性值1” , ”属性名2”:”属性值2”}
callback : 响应成功之后调用函数, 称为回调函数。
ajax局部刷新发生在回调函数中。
该回调函数仅在响应成功并且响应状态码200时,才会调用
Function(data){
Alert(data)
}
type : 设置响应体的类型。(要求,服务器不设置响应体类型)【可以忽略】
type默认值:html
type常用值:text、html、json
JQuery的源码,中的Ajax方法描述
如需复杂的ajax参数设置请使用$.ajax
jQuery.ajax({[settings]})
其中,settings是一个js字面量形式的对象,格式是{name:value,name:value }
常用的name属性名如下:
4、Ajax项目实战
JS技术核心,实际就是在操作这两个对象
ES6新加了几个对象,ES7、8改动很少
index.jsp
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
$Title$
用户名:
AjaxController.java
@Controller
public class AjaxController {
@RequestMapping("/ajax1")
public void ajax1(String name, HttpServletResponse response) throws IOException {
System.out.println("调用成功" + name);
response.getWriter().println("true");
}
}
启动项目测试
查看控制台
过滤器与拦截器的区别
拦截器是AOP思想的具体实现
项目结构
MyInterceptor.java
public class MyInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
System.out.println("===========处理前===========");
// true:放行,执行下一个拦截器
return true;
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
System.out.println("===========处理后===========");
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
System.out.println("===========清理===========");
}
}
springmvc7-interceptor.xml
TestController.java
@Controller
public class TestController {
@RequestMapping("/test1")
public void test1() {
System.out.println("我是test1");
}
}
启动项目测试