当前位置: 首页 > news >正文

Spring MVC 之返回数据(静态页面、非静态页面、JSON对象、请求转发与请求重定向)

文章目录

  • 1. 默认情况下返回静态页面
  • 2. 返回一个非静态页面的数据
    • 2.1 @ResponseBody 返回页面内容
    • 2.2 @RestController = @ResponseBody + @Controller
  • 3. 实现登录功能,返回 JSON 对象
    • 3.1 前端使⽤ ajax,后端返回 json 给前端
    • 3.2 前端发送 JSON 的标准格式
  • 4. 请求转发(forward)或请求重定向(redirect)
    • 4.1 请求转发:forward
    • 4.2 请求重定向:redirect
  • 5. 请求转发和请求重定向的区别

1. 默认情况下返回静态页面

直接在这里返回的,那么返回的就是静态页面的名称,比如

@Controller
public class TestController {@RequestMapping("/sayhi")public String sayHi() {return "hello.html";}
}
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>Document</title>
</head>
<body><h1 style="color: red">我是 hello.html</h1>
</body>
</html>

可以看到前面返回的内容是 hello.html,这里通过一级目录 sayhi,也可以访问到这个页面,说明返回的虽然是 String 类型,但实际上是一个页面
在这里插入图片描述

2. 返回一个非静态页面的数据

2.1 @ResponseBody 返回页面内容

@ResponseBody 可以修饰类也可以修饰方法
修饰类: 表示当前类中的所有方法都会返回一个非静态页面的数据
修饰方法:表示当前方法返回的是一个非静态页面的数据

@Controller
@ResponseBody
public class TestController {@RequestMapping("/sayhi")public String sayHi() {return "hello.html";}
}

在这里插入图片描述

2.2 @RestController = @ResponseBody + @Controller

直接使用 @RestController,代替@ResponseBody 和 @Controller 两个注解,返回页面内容

@RestController
public class TestController {@RequestMapping("/sayhi")public String sayHi() {return "hello.html";}
}

在这里插入图片描述
示例:实现简单计算的功能

<!doctype html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport"content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0"><meta http-equiv="X-UA-Compatible" content="ie=edge"><title>计算器示例</title>
</head>
<body>
<form action="/calc"><h1>计算器</h1>数字1: <input name="num1" type="text"><br>数字2: <input name="num2" type="text"><br><input type="submit" value=" 点击相加 ">
</form>
</body>
</html>
package com.example.demo.controller;import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;@RestController
public class CalcController {@RequestMapping("/calc")public String calc(Integer num1, Integer num2) {if (num1 == null || num2 == null) return "<h1>参数错误!</h1>";return "<h1>结果:" + (num1 + num2) + "</h1><a href='javascript:history.go(-1)'>返回</a>";}}

在这里插入图片描述

3. 实现登录功能,返回 JSON 对象

3.1 前端使⽤ ajax,后端返回 json 给前端

前端代码

<!doctype html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport"content="width=device-width, user-scalable=no, initial-scale=1.
0, maximum-scale=1.0, minimum-scale=1.0"><meta http-equiv="X-UA-Compatible" content="ie=edge"><script src="js/jquery-2.1.4.min.js"></script><title>Document</title><script>// ajax 提交function mysub() {// 判空// var username = $("#username");//这里注意如果在js中有多个 jquery 那么这里的$,是不合适的,$相当于小名,jQuery相当于大名,最好使用大名var username = jQuery("#username");var password = jQuery("#password");if(jQuery.trim(username.val()) == "") {alert("请先输入用户名!");username.focus; // 让光标重置到此元素return;}if(jQuery.trim(password.val()) == "") {alert("请先输入密码!");password.focus();return;}jQuery.ajax({url:"/user/login2",type:"POST",data:{"username":username.val(),"password":password.val()},success:function(result) {alert(JSON.stringify(result));}});}</script>
</head>
<body>
<div style="text-align: center;"><h1>登录</h1>⽤户:<input id="username"><br>密码:<input id="password" type="password"><br><input type="button" value=" 提交 " onclick="mysub()" style="margin-top: 20px;margin-left: 50px;">
</div>
</body>
</html>

后端代码

@Slf4j
@Controller
@ResponseBody  
@RequestMapping("/user") 
public class UserController {@RequestMapping("/login2")public HashMap<String, Object> login2(String username, String password) {HashMap<String, Object> result = new HashMap<>();int state = 200;int data = -1; // 等于1,登录成功,否则登录失败String msg = "未知错误";if(StringUtils.hasLength(username) && StringUtils.hasLength(password)) {if(username.equals("admin") && password.equals("admin")) {data = 1;msg = "";} else {msg = "用户名或密码错误!";}} else { //说明参数为空msg = "非法参数";}result.put("state", state);result.put("data", data);result.put("msg",msg);return result;}
}

在这里插入图片描述
在这里插入图片描述

3.2 前端发送 JSON 的标准格式

在这里插入图片描述

在这里插入图片描述


后端接收 JSON 数据的标准格式:
在这里插入图片描述
在这里插入图片描述

4. 请求转发(forward)或请求重定向(redirect)

通过 return 可以实现跳转,有两种方式

  • forward 请求转发
  • redirect 请求重定向

4.1 请求转发:forward

请求转发是服务器端帮用户实现的

@Controller
public class TestController {//请求转发方式1@RequestMapping("/fw")public String myForward() {return "forward:/hello.html";}//请求转发方式2@RequestMapping("/fw2")public void myForward2(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {request.getRequestDispatcher("/hello.html").forward(request,response);}
}

在这里插入图片描述

4.2 请求重定向:redirect

重定向的请求发生在客户端(浏览器端)

@Controller
public class TestController {//请求重定向方式1@RequestMapping("/rd")public String myRedirect() {return "redirect:/hello.html";}//请求重定向方式2@RequestMapping("/rd2")public void myRedirect2(HttpServletResponse response) throws IOException {response.sendRedirect("/hello.html");}
}

在这里插入图片描述

5. 请求转发和请求重定向的区别

跳转的实现方式有两种:请求转发(Forward)和请求重定向(Redirect)

请求转发就好比:张三(客户端)找李四帮忙(服务器端),而李四说我没空,但我可以让王五帮你的忙,在这个过程中张三只找了一个人,剩下的事情都是李四完成的,这个就是请求转发

请求重定向就好比:张三(客户端)找李四帮忙(服务器端),而李四说我没空,你去要王五帮你的忙吧,于是张三就是找王五帮忙了,这就是请求重定向
具体的区别有下面几点:

  1. 定义:

请求转发: 发生在服务器端的程序中,当服务器收到客户请求后,会先将请求转发给目标地址,然后再将地址返回的结果转发给客户端
请求重定向:服务器端接收到客户端的请求后,会给客户端返回一个临时响应头,这个临时响应头中记录了,客户端需要再次发送请求(重定向)的URL地址,客户端收到地址后,会将请求发送到新的地址中

  1. 数据共享

请求转发是服务器端实现的,整个执行过程,客户端只需要发送一次请求,所以整个交互过程中使用的都是同一个 Request 请求对象和 Response 响应对象,因此请求和返回的数据是共享的
请求重定向客户端发送两次完全不同的请求,所以两次请求中的数据是不同的

  1. 请求方

请求转发是服务器端的行为
请求重定向是客户端的行为(浏览器)

  1. 代码实现不同

  2. 最终的 URL地址

请求转发是服务器端代为请求,所以整个请求过程中 URL 地址是不变的
请求重定向,是服务器端告诉客户端,访问另一个地址,所以浏览器会重新再发送一个请求,因此 URL 地址放生了改变

http://www.lryc.cn/news/3437.html

相关文章:

  • leetcode-每日一题-2335(简单,贪心)
  • Verilog语法之数学函数
  • 【手撕面试题】JavaScript(高频知识点一)
  • 如何用PHP实现消息推送
  • 电子学会2020年6月青少年软件编程(图形化)等级考试试卷(四级)答案解析
  • DaVinci:调色版本
  • 【C++初阶】十二、STL---反向迭代器的实现
  • day 43|● 1049. 最后一块石头的重量 II ● 494. 目标和 ● 474.一和零
  • [SSD固态硬盘技术 0] SSD的结构和原理导论
  • Vue (3)
  • SQL语句,常用的DDL表操作语句
  • C 语言 宏定义 :字符串化 stringify 的应用
  • 代替swagger的api接口神器
  • 2月12日,30秒知全网,精选7个热点
  • HTML img和video object-fit 属性
  • Pascal版本的 - freopen
  • STM32单片机OLED显示
  • 备战金三银四,软件测试面试题(全)
  • 硬件篇-配置
  • 网页内容 中文乱码 解决办法
  • 【C++之容器篇】造轮子:模拟实现vector类
  • C++中的右值引用与移动构造函数
  • Swift如何使用依赖注入进行解藕
  • 合宙ESP32S3-CORE开发板|保姆级|Arduino IDE|windows11|esp32S3支持库|helloword例程:Arduino 环境搭建
  • CMake中target_precompile_headers的使用
  • SpringCloud和微服务介绍
  • Qt源码编译过程中配置文件中的选项说明
  • Mysql 增删改查(一) —— 查询(条件查询where、分页limits、排序order by、分组 group by)
  • VScode 结合clangd 构建linux源代码阅读环境
  • web应用 —— JavaScript