官方对于 Spring MVC 的描述是这样的:
从上述定义我们可以得出两个关键信息:
然而要真正的理解什么是 Spring MVC?我们首先要搞清楚什么是 MVC?
MVC 是 Model View Controller 的缩写,它是软件⼯程中的⼀种软件架构模式,它把软件系统分为模型、视图和控制器三个基本部分。
MVC 是一种思想,而 Spring MVC 是对 MVC 思想的具体实现。总的来说,Spring MVC 是一个实现了 MVC 模式,并继承了 Servlet API 的 Web 框架。
(1) 创建SpringMVC项目
Spring MVC 可以基于 Spring Boot 创建,也就是创建一个 Spring Boot 项目,勾选上 Spring Web 模块即可,详情请参考:
(2) 创建一个 UserController 类,实现用户到 Spring 程序的互联互通,具体实现代码如下:
@Controller
@ResponseBody
@RequestMapping("/user") // 路由映射
public class UserController {
@RequestMapping("/hi")
public String sayHi() {
return "<h1>hi, SpringMVC<h1>";
}
}
@RequestMapping
是 Spring Web 应用程序中最常被用到的注解之⼀,它是用来注册接口的路由映射的。
路由映射:所谓的路由映射指的是,当用户访问⼀个 url 时,将用户的请求对应到程序中某个类的某个方法的过程就叫路由映射。
@ResponseBody
返回的值如果是字符会转换成 text/html
,如果返回的是对象会转换成 application/json
返回给前端。
@ResponseBody
可以用来修饰方法或者是修饰类,修饰类表示类中的所有方法都会返回 html
或者 json
,而不是视图
。
@RequestMapping
默认是 get
方式的请求,如果想接收POST请求,我们可以显示的指定 @RequestMapping
来接收 post
:
@RequestMapping(value = "/hi",method= RequestMethod.POST)
get 请求的 3 种写法:
// 写法1
@RequestMapping("/index")
// 写法2
@RequestMapping(value = "/index",method = RequestMethod.GET)
// 写法3
@GetMapping("/index")
post 请求的 2 种写法:
// 写法1
@RequestMapping(value = "/index",method = RequestMethod.POST)
// 写法2
@PostMapping("/index")
在 Spring MVC 中可以直接用方法中的参数来实现传参,比如以下代码:
@RequestMapping("/showname")
public String showName(String name) {
return "姓名:" + name;
}
在 postman 中模拟传参:
Spring MVC 可以自动实现参数对象的赋值,比如 Person 对象:
创建Person类:
@Data
public class Person {
private int id;
private String name;
private String password;
}
传递对象代码实现:
@RequestMapping("/person")
public Object getPerson(Person person) {
return person;
}
通过url访问并传递参数:
@RequestMapping("/login")
public String login(String username, String password) {
return "用户名:" + username + " 密码:" + password;
}
通过url访问并传递参数:
某些特殊的情况下,前端传递的参数 key 和我们后端接收的 key 可以不一致,比如前端传递了⼀个 time 给后端,而后端又是有 createtime 字段来接收的,这样就会出现参数接收不到的情况,如果出现这种情况,我们就可以使用 @RequestParam
来重命名前后端的参数值。
@RequestMapping("/time")
public String getTime(@RequestParam("time") String createtime) {
return createtime;
}
输入url传递参数:
拿上面的例子,不给time传参数:
就会报400,为什么会这样呢?
看下@RequestParam
源码:
@RequestMapping("/time2")
public String getTime2(@RequestParam(value = "time", required = false) String createtime) {
return createtime;
}
通过url访问并不设置参数:
发现并没有报错,说明设置是有效的。
@RequestMapping(value = "getjson", method = RequestMethod.POST)
public Object getJson(@RequestBody Person person) {
return person;
}
通过postman传递一个json字符串:
成功接收。
@RequestMapping("/geturl/{name}/{password}")
public String getUrl(@PathVariable String name, @PathVariable String password) {
return "名称:" + name + " 密码:" + password;
}
通过url获取参数:
创建 application.yml
配置文件,配置文件保存路径:
# 图片保存路径
myfile:
path: E:/Data/
后端实现代码:
@Value("${myfile.path}")
private String filePath; // 从配置文件中获取文件上传路径
@RequestMapping("/upfile")
public boolean upFile(String name, @RequestPart("myfile") MultipartFile file) {
boolean result = false;
try {
// 得到原文件的名称和后缀
String fileType = file.getOriginalFilename();
if (fileType != null) {
fileType = fileType.substring(fileType.lastIndexOf("."));
}
// 文件保存的名称
String fileName = UUID.randomUUID().toString() + fileType;
file.transferTo(new File(filePath + fileName));
result = true;
log.info(name + ":图片上传成功!");
} catch (IOException e) {
log.error(name + ":图片上传失败!");
}
return result;
}
注意:这里用到了log,要给类上加上
@Slf4j
注解。
用postman上传文件:
文件成功保存到路径下:
控制台也打印成功日志:
获取 Cookie 方法1:
@RequestMapping("/getck")
public void getCookie(HttpServletRequest request) {
Cookie[] cookies = request.getCookies();
Arrays.stream(cookies).forEach(cookie -> {
log.info(cookie.getName() + ":" + cookie.getValue());
});
}
方法2:
@RequestMapping("/getck2")
public String getCookie2(@CookieValue("bite") String bite) {
return bite;
}
获取Header:
@RequestMapping("/header")
public String getHeader(@RequestHeader("User-Agent") String userAgent) {
return userAgent;
}
获取session方法1:
@RequestMapping("/getsess")
public String getSession(HttpServletRequest request) {
String result = "";
HttpSession session = request.getSession(false);
if (session != null && session.getAttribute("SESSION_KEY") != null) {
result = (String) session.getAttribute("SESSION_KEY");
}
return result;
}
方法2:
@RequestMapping("/getsess2")
public String getSession2(@SessionAttribute(required = false, name = "SESSION_KEY") String data) {
return data;
}
设置session:
@RequestMapping("/setsess")
public boolean setSession(HttpServletRequest request) {
boolean result = false;
try {
HttpSession session = request.getSession(true);
session.setAttribute("SESSION_KEY", "java");
result = true;
} catch (Exception e) {
log.error("出现异常:" + e.getMessage());
}
return result;
}
创建前端页面 index.html:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<h1 style="color: blue">hello, SpringMVC</h1>
</body>
</html>
创建控制器 Controller:
@Controller
public class IndexController {
@RequestMapping("/index")
public Object index() {
return "/index.html";
}
}
在浏览器输入url:
@RequestMapping("/map")
@ResponseBody
public HashMap<String, String> mapJson() {
HashMap<String, String> map = new HashMap<>();
map.put("Java", "Java Value");
map.put("MySQL", "MySQL Value");
map.put("Redis", "Redis Value");
return map;
}
return 不但可以返回一个视图,还可以实现跳转,跳转的方式有两种:
forward
:请求转发;redirect
:请求重定向。请求转发和重定向的使用对比:
// 请求重定向
@RequestMapping("/index1")
public String index(){
return "redirect:/index.html";
}
// 请求转发
@RequestMapping("/index2")
public String index2(){
return "forward:/index.html";
}
举例说明 forward 和 redirect
例如,你告诉你男/女朋友你想吃雪糕,如果他/她说好,我给你买,这就是forward请求转发
,如果他/她说自己买去,那么就是redirect重定向
。
forward 和 redirect 具体区别如下:
因篇幅问题不能全部显示,请点此查看更多更全内容