本文介绍如何通过api提交项目缺陷,由于不同project提交缺陷时要求的必填字段值可能不同,如下图,所以我们需要根据project id动态获取创建缺陷时需要的必填字段以及对应的字段值。

一:获取必填字段
根据project id获取必填字段并根据字段类型设置字段值,代码如下
//创建缺陷时所需要的字段,以及设置默认值 public static String getBugCreateMeta(String jiraProjectId) { //api 接口 String url = "http://you jira address:port/rest/api/2/issue/createmeta?projectIds=" + jiraProjectId + "&expand=projects.issuetypes.fields"; //初始值 String issueField = "{\n \"fields\": {\n \"project\": {\n \"id\": \"" + jiraProjectId + "\"\n }"; //除了必填项外 需要的字段 String[] otherRequiredField = {"assignee"}; //接口调用 HttpClientResponse httpClientResponse = httpClient(1, url, ""); JSONObject jsonObject = JSONObject.fromObject(httpClientResponse.getResponseBody().toString()); //接口返回结果示例参考下图 //获取项目信息 JSONArray projects = jsonObject.getJSONArray("projects"); JSONObject project = JSONObject.fromObject(projects.get(0)); //获取所有issue类型 JSONArray issuetypes = project.getJSONArray("issuetypes"); //查找缺陷类型 int bugIssueIndex = 0;//用于保存缺陷类型坐标 for (int i = 0; i < issuetypes.size(); i++) { JSONObject issuetype = JSONObject.fromObject(issuetypes.get(i)); if ("缺陷".equals(issuetype.getString("name"))) { bugIssueIndex = i; //添加类型字段 issueField += replace(jiraFieldOptionTemplate, "issuetype", issuetype); break; } } //获取缺陷类型所有信息 JSONObject issuetype = JSONObject.fromObject(issuetypes.get(bugIssueIndex)); //获取提交缺陷时所有字段 JSONObject fields = issuetype.getJSONObject("fields"); //循环所有字段,并获取默认值 Iterator<String> iterator = fields.keys(); while (iterator.hasNext()) { String key = iterator.next(); //获取字段信息 JSONObject field = fields.getJSONObject(key); //字段是必填且没有设置默认值,则选择默认值 if (ArrayUtils.contains(otherRequiredField, key) || (field.getBoolean("required") && !field.getBoolean("hasDefaultValue"))) { //获取字段类型 JSONObject schema = field.getJSONObject("schema"); if (field.containsKey("allowedValues")) { //如果字段值有可选项,则默认取值第一个 JSONArray allowedValues = field.getJSONArray("allowedValues"); JSONObject allowedValue = JSONObject.fromObject(allowedValues.get(0)); issueField = getIssueField(schema, issueField, key, allowedValue); } else { //字段值默认key issueField = getIssueField(schema, issueField, key, null); } } } //闭环json issueField = issueField + "\n }\n}"; return issueField; } /** * 设置那些类型的字段 * * @param schema * @param issueField * @param key * @param allowedValue * @return */ private static String getIssueField(JSONObject schema, String issueField, String key, JSONObject allowedValue) { //针对字段不同类型,定制不同模板 String jiraFieldArrayTemplate = ",\n \"key\": [\n {\n \"id\": \"jira_id\"\n }\n ]"; String jiraFieldOptionTemplate = ",\n \"key\": {\n \"id\": \"jira_id\"\n }"; String jiraFieldStringTemplate = ",\n \"key\": \"jira_key\""; String jiraFieldUserTemplate = ",\n \"key\": {\n \"name\": \"jira_key\"\n }"; //字段类型,需要可以扩展 switch (schema.getString("type")) { case "array": issueField += replace(jiraFieldArrayTemplate, key, allowedValue); break; case "option": issueField += replace(jiraFieldOptionTemplate, key, allowedValue); break; case "string": issueField += replace(jiraFieldStringTemplate, key, null); break; case "user": issueField += replace(jiraFieldUserTemplate, key, null); break; default: break; } return issueField; } /** * 替换值 * * @param template * @param key * @param allowedValue * @return */ private static String replace(String template, String key, JSONObject allowedValue) { //默认值是key,如果有可选值则获取可选值 String value = key; if (allowedValue != null) { value = allowedValue.getString("id"); } //以这种方式根据key的不同定制值 if (key.equals("customfield_10001")) { value = "10001"; } return StringUtils.replaceEach(template, new String[]{"key", "jira_id"}, new String[]{key, value}); } //url 可使用参数projectIds表示项目id、projectKeys表示项目key、issuetypeIds表示类型Id、issuetypeNames表示类型名称、expand增加展示的字段 //http://jyou jira address:port/rest/api/2/issue/createmeta?projectIds=100001&expand=projects.issuetypes.fields&issuetypeIds=10001
//调用接口返回的结果,根据字段类型、是否必填、是否有默认值进行分析
{
"expand": "projects",
"projects": [
{
"expand": "issuetypes",
"self": "http://you jira address:port/rest/api/2/project/1",
"id": "1",
"key": "abc",
"name": "浙江省国办电子印章专项",
"avatarUrls": {
"48x48": "http://you jira address:port/secure/projectavatar?avatarId=10324"
},
"issuetypes": [
{
"self": "http://you jira address:port/rest/api/2/issuetype/2",
"id": "2",
"description": "gh.issue.story.desc",
"iconUrl": "http://you jira address:port/images/icons/issuetypes/story.svg",
"name": "Story",
"subtask": false,
"expand": "fields",
"fields": {
"summary": {
"required": true,
"schema": {
"type": "string",
"system": "summary"
},
"name": "主题",
"hasDefaultValue": false,
"operations": [
"set"
]
}
}
},
{
"self": "http://you jira address:port/rest/api/2/issuetype/3",
"id": "3",
"description": "",
"iconUrl": "http://you jira address:port/secure/viewavatar?size=xsmall&avatarId=3&avatarType=issuetype",
"name": "缺陷",
"subtask": false,
"expand": "fields",
"fields": {
"customfield_10001": {
"required": true,
"schema": {
"type": "option",
"custom": "com.atlassian.jira.plugin.system.customfieldtypes:select",
"customId": 10001
},
"name": "问题环境",
"hasDefaultValue": false,
"operations": [
"set"
],
"allowedValues": [//该字段值可以展示给用户进行选择
{
"self": "http://you jira address:port/rest/api/2/customFieldOption/3",
"value": "测试环境",
"id": "3"
},
{
"self": "http://you jira address:port/rest/api/2/customFieldOption/4",
"value": "生产环境",
"id": "4"
}
]
}
}
}
]
}
]
}
//getBugCreateMeta 方法返回的结果,该结果在第二步中做为body内容进行提交
{
"fields": {
"project": {
"id": "10001"
},
"issuetype": {
"id": "10002"
},
"summary": "jira_summary",
"reporter": {
"name": "huangtai"
},
"customfield_10003": {
"id": "10003"
},
"customfield_10004": {
"id": "10004"
},
"customfield_10005": [
{
"id": "10005"
}
],
"customfield_10006": {
"id": "10006"
},
"assignee": {
"name": "huangtai"
}
}
}
二、提交缺陷
根据第一步中的返回结果作为请求body,提交缺陷,并获取缺陷key,代码如下
/**
* jira上新增缺陷
*
* @param requestBody 就是getBugCreateMeta方法返回的结果
* @return
*/
public static String addJiraIssue(String requestBody) {
//api接口
String url = "http://you jira address:port/rest/api/2/issue";
//请求接口
HttpClientResponse clientResponse = httpClient(2, url, requestBody);
if (clientResponse != null && "201".equals(clientResponse.getStateCode()) && clientResponse.getResponseBody() != null) {
//解析结果并返回缺陷key
JSONObject jsonObject = JSONObject.fromObject(clientResponse.getResponseBody().toString());
if (jsonObject != null && jsonObject.containsKey("key")) {
return jsonObject.getString("key");
}
}
return null;
}
//接口返回结果
{
"id": "12345",
"key": "abc-1001",
"self": "http://you jira address:port/rest/api/2/issue/12345"
}

总结:按照上面的步骤就可以在其它平台使用api的方式提交缺陷了;有时候需要让用户选择字段值,只需要把allowedValues字段在前端展示给用户选择即可。
更多文章请关注公众号

浙公网安备 33010602011771号