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

如何用Spring Boot RestTemplate调用GraphQL API?解决Bad Request报错

使用Spring Boot RestTemplate调用GraphQL接口报Bad Request的解决方法

问题概述

在Spring Boot应用中通过RestTemplate发送包含查询语句和变量的POST请求到GraphQL接口时,持续收到错误响应:{"errors":[{"message":"Bad request"}]},但相同逻辑用Python的requests库调用可正常获取结果。

问题排查与解决步骤

1. 对齐变量结构与查询字段

对比你的请求内容和Python代码,发现核心差异点,需先修正为与Python版本一致的正确结构:

  • 将sorting对象的by字段改为field,并补充direction字段(示例值为DESC)
  • 将products对象的available字段改为primaryOnly
  • 将查询语句中的Date字段改为releasedDt

2. 正确配置RestTemplate

确保RestTemplate具备正确的JSON序列化能力,添加Jackson消息转换器:

@Configuration
public class RestTemplateConfig {
    @Bean
    public RestTemplate restTemplate() {
        RestTemplate restTemplate = new RestTemplate();
        MappingJackson2HttpMessageConverter converter = new MappingJackson2HttpMessageConverter();
        converter.setObjectMapper(new ObjectMapper()
                .configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false)
                .setSerializationInclusion(JsonInclude.Include.NON_NULL));
        restTemplate.getMessageConverters().add(0, converter);
        return restTemplate;
    }
}

3. 构造请求并发送

方法1:使用DTO封装请求(推荐)

先定义GraphQL请求DTO类:

public class GraphQLRequest {
    private String query;
    private Map<String, Object> variables;

    public GraphQLRequest(String query, Map<String, Object> variables) {
        this.query = query;
        this.variables = variables;
    }

    // 自动生成getter、setter方法
}

然后编写调用逻辑:

@Autowired
private RestTemplate restTemplate;

public void invokeGraphQLApi() {
    String apiUri = "你的GraphQL接口地址";
    
    // 构建与Python一致的查询语句
    String query = """
        query ($filter: SearchFilter!, $limit: Int!, $sorting: SearchSorting!) { 
            search (filter: $filter, limit: $limit, sorting: $sorting) { 
                cursor 
                totalCount 
                documents { 
                    id 
                    title 
                    products { name primaryCode } 
                    count 
                    releasedDt 
                    type { ids } 
                } 
            } 
        }""";

    // 构建正确的变量结构
    Map<String, Object> filter = new HashMap<>();
    Map<String, Object> date = new HashMap<>();
    date.put("dt", "2023-01-01");
    filter.put("date", date);

    Map<String, Object> types = new HashMap<>();
    types.put("ids", List.of("1"));
    filter.put("types", types);

    Map<String, Object> products = new HashMap<>();
    products.put("include", List.of("aaa"));
    products.put("primaryOnly", true);
    filter.put("products", products);

    Map<String, Object> category = new HashMap<>();
    category.put("ids", List.of("A12"));
    filter.put("category", category);

    Map<String, Object> sorting = new HashMap<>();
    sorting.put("field", "DATE");
    sorting.put("direction", "DESC");

    Map<String, Object> variables = new HashMap<>();
    variables.put("filter", filter);
    variables.put("sorting", sorting);
    variables.put("limit", 500);

    // 设置请求头(与Python的getHeaders()保持一致,比如认证信息)
    HttpHeaders headers = new HttpHeaders();
    headers.setContentType(MediaType.APPLICATION_JSON);
    headers.set("Authorization", "Bearer 你的认证令牌"); // 按需添加

    HttpEntity<GraphQLRequest> requestEntity = new HttpEntity<>(new GraphQLRequest(query, variables), headers);
    ResponseEntity<String> response = restTemplate.postForEntity(apiUri, requestEntity, String.class);
    
    // 处理响应结果
    System.out.println(response.getBody());
}

方法2:直接用Map构造请求体

若不想创建DTO类,可直接用Map封装请求内容:

Map<String, Object> requestBody = new HashMap<>();
requestBody.put("query", query);
requestBody.put("variables", variables);

HttpEntity<Map<String, Object>> requestEntity = new HttpEntity<>(requestBody, headers);
ResponseEntity<String> response = restTemplate.postForEntity(apiUri, requestEntity, String.class);

关键注意事项

  • 必须设置请求头Content-Type: application/json,这是GraphQL POST请求的标准要求
  • 变量的字段名、类型需严格匹配GraphQL Schema定义,避免字段名错误
  • 使用Java 15+的多行字符串语法(""")可避免查询语句的转义问题,降低语法错误概率

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.20 01:22:43