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

Spring Rest无法返回字符串列表JSON响应的问题咨询

问题解决与答疑

一、报错原因及解决方案

你遇到的HttpMessageNotWritableException本质是Spring找不到合适的JSON转换器来序列化Arrays$ArrayList(Arrays.asList()返回的内部列表实现),尽管手动添加了Jackson依赖,可能存在以下问题及对应解决方法:

1. 检查Jackson依赖完整性

确保WEB-INF/lib下包含以下3个核心Jackson包(版本需与你的Spring版本匹配,比如Spring 5.x对应Jackson 2.9+,Spring 6.x对应Jackson 2.12+):

  • jackson-core-x.x.x.jar
  • jackson-databind-x.x.x.jar
  • jackson-annotations-x.x.x.jar

2. 配置Spring的JSON消息转换器

如果使用XML配置(dispatcher-servlet.xml),需添加转换器配置:

<mvc:annotation-driven>
    <mvc:message-converters>
        <bean class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter">
            <property name="objectMapper" ref="objectMapper"/>
        </bean>
    </mvc:message-converters>
</mvc:annotation-driven>

<bean id="objectMapper" class="com.fasterxml.jackson.databind.ObjectMapper"/>

如果使用Java配置类,需注册转换器:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter;
import com.fasterxml.jackson.databind.ObjectMapper;

@Configuration
@EnableWebMvc
public class WebConfig {

    @Bean
    public MappingJackson2HttpMessageConverter mappingJackson2HttpMessageConverter() {
        MappingJackson2HttpMessageConverter converter = new MappingJackson2HttpMessageConverter();
        converter.setObjectMapper(new ObjectMapper());
        return converter;
    }
}

3. 可选:替换不可变列表

Arrays.asList()返回的是不可变内部列表,虽非报错直接原因,但可替换为普通ArrayList避免潜在问题:

public List<String> getFruits() {
    List<String> fruits = new ArrayList<>(Arrays.asList("Apple", "Banana", "Pear"));
    return fruits;
}

二、内置集合自动转JSON的说明

字符串数组、List等内置集合支持自动转JSON,但必须满足两个条件:

  • 项目中存在完整的Jackson依赖
  • Spring上下文已正确配置MappingJackson2HttpMessageConverter(Spring Boot会自动配置,但纯Spring MVC需手动配置)

满足条件后,返回List<String>或String[]都会被自动序列化为JSON数组。

三、自定义类型列表的返回方式

返回自定义类型列表不需要强制使用ResponseEntity<T>,直接返回List<Student>即可,Spring会自动序列化。但ResponseEntity的优势在于可以灵活控制响应状态码、响应头,比如返回201创建成功、自定义响应头等。

示例1:直接返回自定义类型列表

先定义Student类:

public class Student {
    private Long id;
    private String name;
    private Integer age;

    // Jackson序列化需要无参构造器
    public Student() {}

    public Student(Long id, String name, Integer age) {
        this.id = id;
        this.name = name;
        this.age = age;
    }

    // Jackson需要Getter方法访问属性
    public Long getId() { return id; }
    public void setId(Long id) { this.id = id; }
    public String getName() { return name; }
    public void setName(String name) { this.name = name; }
    public Integer getAge() { return age; }
    public void setAge(Integer age) { this.age = age; }
}

控制器方法直接返回List:

@GetMapping("/students")
public List<Student> getStudents() {
    List<Student> students = Arrays.asList(
        new Student(1L, "Alice", 20),
        new Student(2L, "Bob", 21)
    );
    return students;
}

示例2:使用ResponseEntity返回自定义类型列表

如需控制响应状态码或头信息:

import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;

@GetMapping("/students-with-status")
public ResponseEntity<List<Student>> getStudentsWithStatus() {
    List<Student> students = Arrays.asList(
        new Student(1L, "Alice", 20),
        new Student(2L, "Bob", 21)
    );
    // 添加自定义响应头,返回200 OK状态码
    HttpHeaders headers = new HttpHeaders();
    headers.add("X-Custom-Header", "Student-List");
    return new ResponseEntity<>(students, headers, HttpStatus.OK);
}

注意:自定义类需满足Jackson序列化要求:

  • 有无参构造器
  • 需要序列化的属性有Getter方法(或用@JsonProperty注解标注字段)

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.16 20:55:14