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

使用JIRA Rest API在Apex中检索JQL结果遇格式问题求助

解决Apex调用JIRA REST API返回415不支持媒体类型错误

问题重现

在Apex中调用JIRA的/rest/api/3/search接口执行JQL查询时,返回415 HTTP错误,提示请求体格式不被支持。原代码如下:

原JiraRestClient类

public class JiraRestClient {

  private static final String JIRA_BASE_URL = 'https://sregmi48.atlassian.net';
  private static final String JIRA_API_TOKEN = 'my_api_code';

  public static HttpResponse getAllIssues(string jqlQuery) {
    HttpRequest request = new HttpRequest();
    request.setEndpoint(JIRA_BASE_URL + '/rest/api/3/search');
    request.setMethod('POST');  // Use GET for searching issues by project key
    request.setHeader('Authorization', 'Basic ' + EncodingUtil.base64Encode(Blob.valueOf('apiToken:' + JIRA_API_TOKEN)));
    request.setHeader('Accept','application/json');
      
    Map<String, Object> requestBodyMap = new Map<String, Object>{
        'jql' => jqlQuery
    };
    String requestBodyJSON = JSON.serialize(requestBodyMap);      
//  String requestBody = '{"jql":{"project":{"key":"' + projectKey + '"}}}';
    request.setBody(requestBodyJSON);
    
      
    System.debug(requestBodyJSON);  

    return new Http().send(request);
  }
}

原测试代码(匿名窗口)

HttpResponse response = JiraRestClient.getAllIssues('project = "JIR"');
if (response.getStatusCode() == 415) {
    String responseBody = response.getBody();
    System.debug('Response Body: ' + responseBody);

    List<String> responseHeaders = response.getHeaderKeys();
    for (String key : responseHeaders) {
        System.debug('Response Header ' + key );
    }
} else {
    String responseBody = response.getBody();
    System.debug('Response Body: ' + responseBody);
}

错误原因

415错误的核心原因是请求未指定Content-Type头。JIRA的POST接口需要明确知道请求体的格式为JSON,原代码仅设置了Accept头(告知服务器返回JSON),但未告知服务器发送的请求体是JSON格式。

另外注意:JIRA的Basic Auth认证格式应为你的邮箱地址:API Token,而非apiToken:API Token,这可能导致后续权限错误,需一并修正。

修复方案

  • 添加Content-Type: application/json请求头,明确告知服务器请求体格式
  • 修正Authorization的认证字符串格式(邮箱+API Token)
  • 保留使用JSON.serialize()自动处理JQL的转义,避免手动拼接JSON的语法错误

修改后的完整代码

修正后的JiraRestClient类

public class JiraRestClient {

  private static final String JIRA_BASE_URL = 'https://sregmi48.atlassian.net';
  private static final String JIRA_EMAIL = 'your-email@example.com'; // 替换为你的JIRA关联邮箱
  private static final String JIRA_API_TOKEN = 'my_api_code'; // 替换为你的API Token

  public static HttpResponse getAllIssues(String jqlQuery) {
    HttpRequest request = new HttpRequest();
    request.setEndpoint(JIRA_BASE_URL + '/rest/api/3/search');
    request.setMethod('POST');
    // 修正Basic Auth格式:邮箱:API Token
    request.setHeader('Authorization', 'Basic ' + EncodingUtil.base64Encode(Blob.valueOf(JIRA_EMAIL + ':' + JIRA_API_TOKEN)));
    request.setHeader('Accept','application/json');
    // 添加Content-Type头,指定请求体为JSON
    request.setHeader('Content-Type','application/json');
      
    Map<String, Object> requestBodyMap = new Map<String, Object>{
        'jql' => jqlQuery
    };
    String requestBodyJSON = JSON.serialize(requestBodyMap);      
    request.setBody(requestBodyJSON);
    
    System.debug('Request Body: ' + requestBodyJSON);  

    return new Http().send(request);
  }
}

测试代码(匿名窗口)

HttpResponse response = JiraRestClient.getAllIssues('project = "JIR"');
System.debug('Status Code: ' + response.getStatusCode());
if (response.getStatusCode() == 200) {
    // 解析返回的JSON结果
    Map<String, Object> resultMap = (Map<String, Object>)JSON.deserializeUntyped(response.getBody());
    System.debug('Total Issues: ' + resultMap.get('total'));
} else {
    System.debug('Error Response: ' + response.getBody());
}

额外说明

  • 如果使用GET请求调用JIRA搜索接口,JQL可以直接作为URL参数传递,此时不需要请求体,也不需要Content-Type头,但GET请求的URL长度有限制,复杂JQL建议用POST
  • 确保你的API Token有足够的权限访问目标JIRA项目的搜索接口

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.24 13:43:16