You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring Boot返回JSON响应时如何为结果添加指定键?

嘿,这个问题我之前做Spring Boot项目时也遇到过,用Jackson的注解或者几个低代码方案就能轻松解决,给你分享几个实用的办法:

方案1:用@JsonRootName注解+全局配置(最直接的类级绑定)

如果你想让某个实体类的所有JSON响应都带上同一个专属键,直接在类上标注@JsonRootName指定键名就行,再配合Spring Boot的Jackson开启根包装配置,一步到位。

举个例子,假设你的实体类是User:

import com.fasterxml.jackson.annotation.JsonRootName;

@JsonRootName("user_profile") // 这里填你想要的专属键名
public class User {
    private String username;
    private Integer age;
    
    // 省略getter、setter和构造方法
}

然后在application.yml(或application.properties)里开启根包装:

  • YAML格式:
spring:
  jackson:
    serialization:
      wrap-root-value: true
  • Properties格式:
spring.jackson.serialization.wrap-root-value=true

这样接口返回的JSON就会自动带上你指定的专属键:

{
  "user_profile": {
    "username": "ts178",
    "age": 28
  }
}

方案2:通用包装类(局部灵活处理)

如果不想全局开启根包装,或者只是部分接口需要专属键,写一个通用的响应包装类是更灵活的选择,复用性还强。

比如写一个简单的包装类:

import com.fasterxml.jackson.annotation.JsonProperty;

public class ApiResponse<T> {
    @JsonProperty("result") // 这里定义专属键名
    private T data;

    public ApiResponse(T data) {
        this.data = data;
    }

    // 省略getter
}

然后在Controller里直接返回这个包装类的实例:

@GetMapping("/user")
public ApiResponse<User> getUserInfo() {
    User user = new User("ts178", 28);
    return new ApiResponse<>(user);
}

返回的JSON结果就是:

{
  "result": {
    "username": "ts178",
    "age": 28
  }
}

甚至图省事的话,你也可以直接在Controller里返回一个Map,比如:

@GetMapping("/user")
public Map<String, User> getUserInfo() {
    User user = new User("ts178", 28);
    return Collections.singletonMap("result", user);
}

这个写法更轻量,适合临时快速实现。

方案3:自定义序列化器(复杂场景适配)

如果你的需求比较特殊——比如同一个实体类在不同接口需要不同的专属键,那可以自定义Jackson序列化器。不过这个方案一般用在复杂场景,前面两种足够应付大多数情况了。

举个简单的自定义序列化器例子:

import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.SerializerProvider;
import com.fasterxml.jackson.databind.ser.std.StdSerializer;

import java.io.IOException;

public class UserCustomSerializer extends StdSerializer<User> {
    private final String rootKey;

    // 允许传入不同的专属键名
    public UserCustomSerializer(String rootKey) {
        super(User.class);
        this.rootKey = rootKey;
    }

    @Override
    public void serialize(User user, JsonGenerator gen, SerializerProvider provider) throws IOException {
        gen.writeStartObject();
        gen.writeObjectField(rootKey, user);
        gen.writeEndObject();
    }
}

然后在需要的地方指定使用这个序列化器:

@GetMapping("/user/detail")
public User getUserDetail() {
    User user = new User("ts178", 28);
    ObjectMapper mapper = new ObjectMapper();
    SimpleModule module = new SimpleModule();
    module.addSerializer(User.class, new UserCustomSerializer("user_detail"));
    mapper.registerModule(module);
    // 这里可以用mapper把对象转成JSON字符串返回,或者结合Spring的配置全局生效
    return user;
}

总结

如果是全局统一给某个实体类加专属键,方案1最省心;如果是局部接口需要,方案2的包装类或Map写法最简洁低代码;复杂场景再考虑方案3。

内容的提问来源于stack exchange,提问作者ts178

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.19 03:42:09