一、认识 Spring MVC

1.1 MVC设计模式

MVC是Model-View-Controller的缩写,是软件工程中一种经典的分层架构模式,核心是将软件系统拆分为三个职责明确的部分,实现“关注点分离”。

  • Model(模型):应用程序的“大脑”,负责处理业务逻辑和数据管理。比如电商系统中计算订单金额、从数据库查询用户信息的逻辑,都属于Model层。
  • View(视图):应用程序的“脸面”,负责与用户交互、展示数据。浏览器中的页面、App的界面都属于View层,它只关注“如何显示”,不关心“数据从哪来、怎么处理”。
  • Controller(控制器):应用程序的“调度员”,负责接收用户请求,协调Model和View工作。比如用户点击“提交订单”按钮后,Controller会调用Model层处理订单逻辑,再指定View层展示订单提交结果。
    在这里插入图片描述

1.2 Spring MVC

MVC是一种思想,而Spring MVC是这种思想在Web开发中的具体实现,同时它还是一个功能完备的Web框架。它的关注点有两个:

  1. 遵循MVC模式:但在前后端分离的主流开发模式下,View层的职责被弱化——后端不再返回完整页面,而是返回JSON、文本等数据,让前端自行渲染页面。
  2. Web框架能力:能够接收浏览器的HTTP请求、解析请求参数、处理业务逻辑,最终返回响应结果,实现浏览器-后端程序的交互。

在这里插入图片描述

1.3 Spring Boot与Spring MVC的关系

Spring Boot和Spring MVC是“容器与工具”的关系:

  • Spring Boot是一个“快速开发脚手架”,它能简化项目配置,但本身不直接提供Web功能;
  • Spring MVC是实现Web功能的“工具”,Spring Boot通过引入spring-web依赖,让项目拥有处理HTTP请求的能力。

类比:Spring Boot像“厨房”,提供了做饭的基础环境;Spring MVC像“燃气灶+锅铲”,是实现“做饭(Web功能)”的工具。


二、 建立连接:让浏览器找到程序

建立连接的核心是URL路由映射,当用户访问某个URL时,Spring MVC能将请求转发到对应的Java方法上。实现这一功能的注解是 @RequestMapping

2.1 基础用法:绑定URL与方法

通过@RequestMapping注解,可以指定一个URL路径,让该路径的请求触发对应的方法。同时,需要用@RestController注解标记类,告诉Spring“这个类是控制器,需要扫描其中的路由方法”。

// 标记类为控制器,且所有方法返回数据(非页面)
@RestController
public class UserController {
    // 绑定URL:http://127.0.0.1:8080/hello
    @RequestMapping("/hello")
    public String hello() {
        return "Hello, Spring MVC!";
    }
}

访问http://127.0.0.1:8080/hello,浏览器显示Hello, Spring MVC!,表示连接建立成功。

2.2 进阶用法:类+方法的路径组合

@RequestMapping既可以修饰类,也可以修饰方法,最终的资源路径是 “类路径+方法路径”,适合按模块划分URL。

@RestController
// 类路径:所有方法的URL都以“/user”开头
@RequestMapping("/user")
public class UserController {
    // 方法路径:完整URL为“/user/hello”
    @RequestMapping("/hello")
    public String hello() {
        return "Hello, User Module!";
    }
}

访问http://127.0.0.1:8080/user/hello,触发该方法。

这种方式可以避免重复的RequestMapping发生错误,也可以增加可读性

2.3 指定请求方式(GET/POST)

@RequestMapping默认支持GET、POST等所有请求方式,若需限制请求方式,可通过method属性指定。如果参数只给定字符串,默认赋值给value

  • 只允许POST请求:
@RequestMapping(value = "/addUser", method = RequestMethod.POST)
public String addUser() {
    return "User added successfully!";
}

//另一种方式:使用@PostMapping注解
@PostMapping( "/addUser")
public String addUser() {
    return "User added successfully!";
}

此时用GET方式访问/addUser会报错,只有POST请求才能正常触发。

  • 限制多个方式:
@RequestMapping(value = "/addUser", method = {RequestMethod.POST,RequestMethod.GET})
public String addUser() {
    return "User added successfully!";
}

三、 获取请求参数:解析浏览器传递的数据

用户发送请求时,往往会携带参数(登录时的用户名、密码),Spring MVC提供了多种方式获取这些参数,覆盖不同的参数传递场景。

3.1 单个/多个普通参数

直接在方法中定义与参数名一致的形参,Spring MVC会自动将请求参数赋值给形参。

@RestController
@RequestMapping("/param")
public class RequestController{
    // 单个参数:URL: http://127.0.0.1:8080/param/m1?name=zhangsan
    @RequestMapping("/m1")
    public String method1(String name) {
        return "接收的参数name:" + name;
    }

    // 多个参数:URL: http://127.0.0.1:8080/param/m2?name=zhangsan&password=123456
    @RequestMapping("/m2")
    public String method2(String name, String password) {
        return "接收的参数:name=" + name + ", password=" + password;
    }
}

注意

  1. URL中参数顺序不影响赋值,Spring MVC通过参数名匹配;
  2. 若参数是int等基本类型,必须传递参数;如果是Integer等包装类型,不传参数时为null,因此采用包装类型更合适

3.2 传递对象参数

当参数较多,例如用户注册包括用户名、密码、年龄、邮箱,可以将参数封装为Java对象,Spring MVC会自动根据参数名匹配对象的属性并赋值。

  1. 定义User类(封装参数):
public class User {
    private String name;
    private String password;
    private Integer age;
    // getter、setter、构造方法
}
  1. 控制器方法:
@RequestMapping("/m3")
public String method3(User user) {
    return "接收的用户信息:" + user.getName() + ", " + user.getAge();
}

访问URLhttp://127.0.0.1:8080/param/m3?name=zhangsan&password=123456&age=20,Spring MVC会自动创建User对象实例并赋值。

注意: 对于int 类型参数,必须传参;对象中的int字段作为参数,可以不传参,默认是0。

3.3 接受数组参数

    @RequestMapping("/r5")
    public String r5(String[] arr){
        return "arr:"+ Arrays.toString(arr);
    }  

Pasted image 20260713094923.png

当客户端传递多个参数名相同的数值时,后端会组装成数组。

可以分别传入多个arr元素,也可以传入一个参数,使用逗号分割多个元素,Spring MVC会自动拆分逗号分隔字符串,并入数组。

3.4 参数绑定(@RequestParam)

@RequestParam主要有两个作用:参数重命名和接收集合参数

参数重命名:
当前端传递的参数名与后端方法的形参名不一致时(比如前端传p,后端用password接收),可以用 @RequestParam 注解重命名参数。

@RequestMapping("/m4")
public String method4(@RequestParam("p") String password) {
    return "接收的创建时间:" + password;
}

此时前端的参数必须是p,传入password就会报错,无法匹配参数。

属性

  • value:指定前端传递的参数名;
  • required:默认true(参数必传),若参数非必传,可设置为false@RequestParam(value = "p", required = false))。
  • defaultValue:指定没有传入的参数的默认值

3.5 传递集合参数(@RequestParam)

传递集合时要加上参数绑定注解@RequestParam ,明确告诉 Spring 从请求参数中获取数据并封装到 list

    @RequestMapping("/r6")
    public String r6(@RequestParam ArrayList<Integer> list){
        return "list:"+ list.toString();
    }

3.6 接收JSON参数(@RequestBody)

JSON

JSON(JavaScript Object Notation)是一种轻量级的数据交换格式,易于人阅读和编写,同时也易于机器解析和生成。它基于JavaScript的一个子集,但采用了独立于编程语言的文本格式,几乎所有编程语言都有相应的库来处理JSON,因此成为跨平台数据交换的常用格式。

基本结构

JSON数据由两种基本结构组成:

  1. 键值对集合:类似对象(Object),用大括号 {} 包裹,内部是一系列 key: value 键值对,键和值之间用冒号分隔,多个键值对用逗号分隔。

    • 键(key)必须是字符串,用双引号 "" 包裹。
    • 值(value)可以是以下类型:字符串(双引号包裹)、数字、布尔值(true/false)、null、对象(嵌套)、数组。
  2. 有序值列表:类似数组(Array),用方括号 [] 包裹,内部是有序的值,多个值用逗号分隔,值的类型同上。

代码使用

Spring boot 提供了JSON与对象之间转换方法:

public class JSONTest {
	//对象转Json
    @Test
    void Object2Json() throws JsonProcessingException {
        ObjectMapper mapper = new ObjectMapper();

        //创建对象
        UserInfo userInfo = new UserInfo();
        userInfo.setName("daisy");
        userInfo.setAge(18);
        userInfo.setGender(1);

        //对象转json
        String s = mapper.writeValueAsString(userInfo);
        System.out.println(s);
    }
		
	//Json转对象
    @Test
    public void Json2Object() throws JsonProcessingException {
        ObjectMapper mapper = new ObjectMapper();
        String s = "{\"name\":\"daisy\",\"age\":18,\"gender\":1}";
        UserInfo userInfo = mapper.readValue(s,UserInfo.class);
        System.out.println(userInfo);
    }
}

JSON 的特点

  • 简洁性:相比 XML,语法更简单,冗余更少。
  • 可读性:结构清晰,易于人类理解。
  • 跨语言:几乎所有编程语言都支持 JSON 的解析和生成。
  • 轻量性:适合网络传输,减少数据体积。(PB更加轻量,性能高,但是是二进制编码,可读性差)

接收JSON参数

在前后端分离项目中,前端常以JSON格式传递复杂参数(嵌套对象),此时需要用@RequestBody注解标记方法参数,告诉Spring MVC“从请求体中解析JSON数据”。

  • 控制器方法:
    @RequestMapping("/r7")
    public String r7(@RequestBody UserInfo userInfo){
        return  userInfo.toString();
    }
  • 前端传递的JSON数据(通过postman发送请求):
{
    "name": "daisy",
    "gender": 1,
    "age": 18
}

注意

  1. @RequestBody只能解析请求体中的JSON数据,无法解析URL中的参数;并且请求的Content-Type需设置为application/json
  2. 对于Jackson 解析框架:使用无参构造方法 + setter 方法来创建对象;如果对象只定义了有参构造方法,且没有 setter 方法,默认情况下会解析失败
  3. 前端无法解析对象,所以后端返回的MapList,或其他对象Spring返回的都是JSON
  4. JSON中的键值对顺序可以与对象的属性不一一对应,但是键必须与对象中的属性一致

3.7 接收URL路径参数(@PathVariable)

有时参数会直接包含在URL路径中(比如/article/1000表示查询ID为1000的文章),此时需要用@PathVariable注解获取路径中的参数。

// URL:http://127.0.0.1:8080/request/article/1100/blog
    @RequestMapping("/article/{articleId}/{type}")
    public String r8(@PathVariable Integer articleId,@PathVariable String type){
        return "articleId:"+articleId+" type:"+type;
}

注意:

  • 参数是必传参数。如果不传入参数,就会导致找不到资源路径,404报错
  • 若方法形参名与URL中的变量名一致(type),@PathVariable可省略属性;
  • 若不一致(URL中是type,方法中是articleType),需通过value指定URL变量名(@PathVariable("type"))。

3.8 接收文件参数(@RequestPart)

    @RequestMapping("/r9")
    public String r9(MultipartFile file) throws IOException {
    	//文件上传
        file.transferTo(new File("D:\\temp\\"+file.getOriginalFilename()));
        return "文件上传成功";
    }

可以通过@RequestPart对文件进行重命名 :

    @RequestMapping("/r9")
    public String r9(@RequestPart(f) MultipartFile file) throws IOException {
        file.transferTo(new File("D:\\temp\\"+file.getOriginalFilename()));
        return "文件上传成功";
    }

3.9 Cookie / Session

HTTP协议的“无状态”是指:服务器对每一次请求的处理都是独立的,不会保留上一次请求的任何信息

为了在无状态的HTTP协议上实现“状态保持”,Cookie和Session应运而生:

  • Cookie:将状态数据存储在客户端(浏览器),每次请求时自动携带;
  • Session:将状态数据存储在服务器,客户端仅保存一个标识(通常是SessionID)。

二者本质是“客户端存储”与“服务器存储”的分工,共同解决Web应用的状态管理问题.

Cookie

Cookie是服务器发送给浏览器的小型文本数据,浏览器通常将其保存在本地文件中,并在后续向该服务器发送请求时,自动携带这些数据。

Cookie的工作流程

Cookie的交互过程可分为3步,类似“图书馆借书”的场景:

  1. 首次请求:用户第一次访问服务器(登录页面),此时浏览器没有相关Cookie,请求中不携带任何状态信息;
  2. 服务器生成Cookie:服务器处理请求后,在响应中附加Cookie(包含用户标识的信息),并通过Set-Cookie响应头发送给浏览器;
    • 类比:图书馆给用户一张“会员卡”(Cookie),卡上记录用户ID;
  3. 后续请求:浏览器收到Cookie后保存,此后每次访问该服务器时,都会在请求头Cookie中携带这些数据;
    • 类比:用户再次借书时,自动出示会员卡,图书馆通过卡号识别用户。
Cookie的核心属性

每个Cookie都包含一系列属性,其中name和value可以手动指定,区域属性都是系统默认的。

  1. name Cookie 名称,同一域名+路径下名称唯一;仅靠 name 无法全局唯一,需配合 domain、path 三者组合才能区分不同 Cookie。
  2. value Cookie 存储的实际数据,SessionID、用户标识等内容均存放于此;业务敏感数据建议加密存储,禁止明文存放隐私信息。
  3. domain 限定 Cookie 生效域名,控制请求时是否自动携带该 Cookie;若设置为 example.com,则其子域名 a.example.com 也能携带此 Cookie;不手动指定时,默认值为设置 Cookie 的当前域名。
  4. path 限定 Cookie 生效路径,仅请求路径匹配或包含该前缀时,浏览器才会自动带上 Cookie;例:path=/user,仅访问 /user/user/info 等子路径会携带,访问 /home 不会携带。
  5. Max-Age 单位为秒,用于设置 Cookie 相对过期时间,优先级高于旧版 expires 属性:
  • 正整数:Cookie 创建后,经过对应秒数永久存储,超时自动清除;
  • 等于 0:浏览器收到后立刻删除该 Cookie;
  • 负数(默认未显式配置):属于会话 Cookie,仅当前浏览器标签/进程存活期间有效,完全关闭浏览器后自动销毁,无持久化存储。
  1. Secure 布尔属性,值为 true 时,浏览器仅在 HTTPS 加密请求中携带该 Cookie;HTTP 明文请求不会发送,用于防止明文传输泄露 Cookie。
  2. HttpOnly 布尔属性,开启后浏览器禁止前端 JS(document.cookie)读取、修改该 Cookie;可有效抵御 XSS 跨站脚本攻击,避免脚本窃取会话标识(如 SessionID)。

后端接收到的参数有多种来源:

  1. url请求参数:http://xxx/param
  2. url资源路径:http://xxx?param
  3. header:cookie,session
  4. 请求正文body:JSON,文件
    Session(会话)是服务器为每个用户创建的内存存储空间,用于保存用户的状态信息(例如登录状态、购物车数据)。服务器会为每个Session分配一个唯一标识(SessionID),并通过Cookie将SessionID发送给客户端——客户端只需保存SessionID,实际数据存储在服务器。

Session

Session的本质就是⼀个 “哈希表”, 存储了⼀些键值对结构. Key 就是SessionID, Value 就是用户信息。

Session的工作流程

Session的交互过程比Cookie多一步服务器端存储,类似“超市储物柜”:

  1. 首次请求:用户第一次访问服务器,服务器创建一个Session(生成唯一SessionID),并将SessionID通过Cookie发送给浏览器;
    • 类比:超市给用户一个带编号的储物柜钥匙(SessionID),柜子(Session)由超市保管;
  2. 存储数据:服务器将用户状态(如登录信息)存入该Session;
    • 类比:用户将物品(状态数据)放入对应编号的柜子;
  3. 后续请求:浏览器携带SessionID(通过Cookie)访问服务器,服务器根据SessionID找到对应的Session,获取存储的状态数据;
    • 类比:用户用钥匙(SessionID)打开对应的柜子,取出物品。

在这里插入图片描述

Session的核心特性
  • 服务器存储:数据保存在服务器(内存、数据库等),客户端仅保存SessionID,安全性高于Cookie;
  • 会话隔离:每个用户的Session独立,数据互不干扰;
  • 有效期:默认有效期为30分钟(可配置),超时未活动会自动销毁;
  • 依赖Cookie:默认通过Cookie传递SessionID(若浏览器禁用Cookie,需通过URL重写传递,现已很少使用)。

注意: Session 默认是保存在内存中的. 如果重启服务器则 Session 数据就会丢失

Cookie与Session的对比

  • Cookie 是客户端保存用户信息的一种机制. Session 是服务端保存用户信息的一种机制.
  • Cookie 和 Session之间主要是通过 SessionId 关联起来的, SessionId 是 Cookie 和 Session 之间的桥梁
  • Cookie 和 Session 经常会在一起配合使用. 但是不是必须配合.
    • 完全可以用 Cookie 来保存一些数据在客户端. 这些数据不一定是用户身份信息, 也不一定是 SessionId
    • Session 中的sessionId 也不需要非得通过 Cookie/Set-Cookie 传递, 比如通过URL传递.
维度 Cookie Session
存储位置 客户端(浏览器) 服务器端
安全性 较低,数据在客户端,易被篡改 较高,数据在服务器,仅传递SessionID
存储大小 有限制,通常4KB以内 无严格限制,受服务器内存/存储影响
性能影响 每次携带 ,增加请求体积 占用服务器资源,大量用户时需优化
有效期 可长期保存(通过maxAge设置) 通常短期有效,超时自动销毁

3.10 HttpServletRequest / HttpServletResponse

在Servlet与Spring MVC体系中,一次完整HTTP请求处理流程依靠两大对象承载数据:HttpServletRequest(请求对象)、HttpServletResponse(响应对象),所有Cookie、Session、请求头、参数、页面跳转、返回数据的操作都离不开这两个对象心。

HttpServletRequest

代表客户端→服务器的请求报文,浏览器发送的所有信息都会被框架自动封装进该对象

常用功能:

  1. 读取CookiegetCookies() 获取请求携带的全部Cookie数组,是服务端接收客户端Cookie的唯一原生方式;
  2. 操作SessiongetSession() 依据请求里的JSESSIONID获取会话对象,区分创建/不创建Session两种重载;
  3. 获取请求头getHeader("头名称") 读取User-Agent、token、设备标识等自定义/标准请求头;
  4. 接收请求参数getParameter() 获取GET/POST普通表单参数;
  5. 获取请求基础信息:请求地址、请求方式、客户端IP、端口等。

HttpServletResponse

代表服务器→客户端的响应报文,服务端想传递给浏览器的数据、指令都通过该对象设置,核心能力:

  1. 下发CookieaddCookie(Cookie) 往响应头添加Set-Cookie字段,浏览器收到后自动保存/覆盖本地Cookie;
  2. 设置响应状态、响应头:自定义响应头、404/200/302等状态码;
  3. 页面跳转sendRedirect() 重定向跳转页面;
  4. 输出响应内容:输出字符串、JSON、文件流给前端。

两者与Cookie、Session、请求头的关联

  1. Cookie双向交互:
    • 读Cookie:用 HttpServletRequest 拿客户端上传的Cookie;
    • 写/删Cookie:用 HttpServletResponse 给浏览器下发新Cookie覆盖旧数据;
  2. Session底层依赖Request: Session本质依靠名为JSESSIONID的Cookie传递会话标识,所有获取、操作Session的入口都在HttpServletRequest;销毁Session仅需调用Session自身invalidate(),无需Response;
  3. 请求头读取仅靠Request: 浏览器携带的请求头全部封装在HttpServletRequest@RequestHeader注解底层也是封装调用request.getHeader()简化开发。

3.11 接收Cookie

通过@CookieValue注解直接获取指定名称的Cookie值,或通过HttpServletRequestgetCookies()方法遍历所有Cookie。

  • 遍历所有Cookie:适合不确定Cookie名称的场景
@GetMapping("/r10")
public String r10(HttpServletRequest request) {
    StringBuilder sb = new StringBuilder();
    Cookie[] cookies = request.getCookies();
    if (cookies != null) {
        for (Cookie cookie : cookies) {
        sb.append(cookie.getName()).append(":").append(cookie.getValue());
        }
    } else {
        sb.append("请求中没有携带Cookie");
    }
    return sb.toString();
}
  • @CookieValue获取指定Cookie
@GetMapping("/r11")
public String r11(@CookieValue(value = "userId") String userId) {
    return "当前登录用户ID:" + userId;
}

3.12 接收Session

Spring MVC提供了多种操作Session的方式,最常用的是HttpSession对象和@SessionAttribute注解。

存储Session数据

通过HttpSessionsetAttribute()getAttribute()方法操作数据。

    @RequestMapping("/r12")
    public String setSession(HttpServletRequest request){
        //从cookie中获取sessionId,再根据sessionId获取session对象
        HttpSession session = request.getSession();
        
        //默认存在内存中
        session.setAttribute("userName","daisy");
        session.setAttribute("password","1234");
        return "设置session成功";
    }

点开getSession我们会发现有两个方法:
在这里插入图片描述
无参的方法,var1值默认为true

  • true:没有获取到Session时,返回一个空的Session独对象
  • false:没有获取到Session时,返回null

获取Session数据

  • 方式一:通过HttpServletRequest获取:

如果在查询sessionid之前已经设置过session属性,就可以视作用户已登录

    @RequestMapping("/getSession")
    public String getSession(HttpServletRequest request) {
        //从cookie中获取sessionId,再根据sessionId获取session对象
        HttpSession session = request.getSession(false);
        //如果用户登陆,session不为空,如果用户未登录,返回null

        String userName;
        if (session == null) {
            return "用户未登录";
        } else {
            //从session中获取用户信息
            userName = session.getAttribute("userName").toString();

        }
        return "登录用户:" + userName;
    }
  • 方式二:通过HttpSession获取:
    @RequestMapping("/getSession2")
    public String getSession2(HttpSession session){
        String userName = session.getAttribute("userName").toString();
        return "登录用户:"+userName;
    }

HttpSession sessionHttpServletRequest request; request.getSession(true)等价。可以省略对session对象为空的校验

  • 方式三:通过@SessionAttribute获取:
    @RequestMapping("/getSession3")
    public String getSession3(@SessionAttribute("username") String username){
        return "登录用户:"+username;
    }

@SessionAttribute("username") String username session.getAttribute("userName")等价

3.13 接收header(@RequestHeader)

  • 方式一:通过request.getHeader()获取HTTP请求头中的信息
    @RequestMapping("/getHeader")
    public String getHeader(HttpServletRequest request){
        String userAgent = request.getHeader("user-Agent");
        return "从header中获取userAgent::"+userAgent;
    }
  • 方式二:通过 @RequestHeader获取
    @RequestMapping("/getHeader2")
    public String getHeader2(@RequestHeader("User-Agent")String userAgent){
        return "从header中获取userAgent::"+userAgent;
    }

四 返回响应结果:给浏览器返回数据或页面

处理完业务逻辑后,需要将结果返回给前端,Spring MVC支持返回文本、JSON、HTML片段、静态页面等多种响应类型.

1. @RestController / @Controller

@Controller@RestController@ResponseBody是用于标识控制器类的注解,它们的作用是将类标记为处理 HTTP 请求的组件:

  1. @Controller

    • 响应处理:默认情况下,@Controller 标注的类中,方法的返回值通常是视图名称,Spring 会根据视图解析器渲染对应的页面并返回给客户端。
    • 返回数据:如果需要直接返回数据(JSON、XML )而非视图,需要在方法上额外添加 @ResponseBody 注解,此时方法返回值会被直接转换为响应体。
  2. @RestController

    • 功能本质@RestController@Controller@ResponseBody组合注解,等价于 @Controller + @ResponseBody
    • 响应处理:标注此类后,所有方法的返回值都会直接作为响应体(无需再单独加 @ResponseBody),适用于构建 RESTful API(返回 JSON/XML 等数据),而非渲染页面。
    • 典型场景:前后端分离项目中,后端仅提供数据接口,不负责页面渲染时使用。
  3. @ResponseBody

    • 单独使用时,通常加在 @Controller 标注的类的方法上,作用是将方法返回值直接转换为 HTTP 响应体,常用于既需要返回页面,也需要返回数据这种混合场景。
    • 既是类注解,也是方法注解。作为类注解时,表示整个类的方法都返回数据;作为方法注解时,表示这个方法返回数据。。

对比

  • 类中所有方法都返回页面@Controller
  • 类中所有方法都返回数据@RestController,也可以使用@Controller+@responseBody,不可以只用@responseBody,因为不会被启动类扫描到;
  • 类中部分方法返回页面,部分方法返回数据,类注解使用 @Controller ,方法注解使用@ResponseBody

返回页面:

// 标记为控制器,默认返回页面
@Controller
public class PageController {
    // 返回static目录下的index.html页面
    @RequestMapping("/index")
    public String index() {
        return "/index.html";
    }

    // 单独添加 @ResponseBody,返回数据
    @RequestMapping("/returnData")
    @ResponseBody
    public String returnData() {
        return "这是返回的数据,不是页面";
    }
}

2. 返回JSON数据

Spring MVC会自动将Java对象转换为JSON格式返回,无需手动处理。

@RequestMapping("/returnJson")
@ResponseBody
public HashMap<String, String> returnJson() {
    HashMap<String, String> data = new HashMap<>();
    data.put("name", "zhangsan");
    data.put("role", "admin");
    return data;
}

访问该接口,浏览器会返回JSON格式数据:{"name":"zhangsan","role":"admin"},且响应头Content-Type会自动设置为application/json

3. 返回HTML片段

若返回的字符串包含HTML标签,Spring MVC会将其作为HTML片段返回,浏览器会自动解析渲染。

@RequestMapping("/returnHtml")
@ResponseBody
public String returnHtml() {
    return "<h1>一级标题</h1>";
}

浏览器会显示带有标题和段落的页面,响应头默认为Content-Typetext/html

可以修改为@RequestMapping(value = "r3",produces = "text/plain"),这样就不会被渲染,是纯文本格式

![[Pasted image 20260713094626.png|400 ]]

4. 手动设置响应状态码

Spring MVC会自动根据请求结果设置状态码,例如成功返回200,参数错误返回400,也可通过HttpServletResponse参数手动设置状态码。

@RequestMapping("/setStatus")
@ResponseBody
public String setStatus(HttpServletResponse response) {
    // 设置状态码为401(未授权)
    response.setStatus(401);
    return "状态码已设置为401";
}

注意: 状态码不影响页面展示。

5. 手动设置Header

@RequestMapping("/setHeader")
@ResponseBody
public String setHeader(HttpServletResponse response) {
    response.setHeader("myHeader","myHeader");
    return "设置myHeader";
}
Logo

Agent 垂直技术社区,欢迎活跃、内容共建。

更多推荐