【问题标题】:Java - HTTP Post Jira API - Bad RequestJava - HTTP Post Jira API - 错误请求
【发布时间】:2016-08-31 11:11:26
【问题描述】:

我有此代码可以对 Jira URL (https://xxxxxxx.atlassian.net/rest/api/2/issue/) 执行 HTTP Post:

    Object jsonMessage = arg0.getMessage().getPayload();

    URL url = new URL(jiraUrl + jiraIssuePath);

    HttpsURLConnection conn = (HttpsURLConnection) url.openConnection();

    BASE64Encoder enc = new sun.misc.BASE64Encoder();
    String userpassword = jiraUsername + ":" + jiraPassword;
    String encodedAuthorization = enc.encode(userpassword.getBytes());
    conn.setDoOutput(true);
    conn.setDoInput(true);
    conn.setRequestProperty("Authorization", "Basic " + encodedAuthorization);
    conn.setRequestProperty("Content-Type", "application/json;charset=UTF-8");

    conn.setRequestMethod("POST");

    OutputStreamWriter wr = new OutputStreamWriter(conn.getOutputStream());
    wr.write(jsonMessage.toString());
    wr.flush();

    StringBuilder sb = new StringBuilder();
    int HttpResult = conn.getResponseCode();
    if (HttpResult == HttpsURLConnection.HTTP_OK) {
        BufferedReader br = new BufferedReader(new InputStreamReader(conn.getInputStream(), "utf-8"));
        String line = null;
        while ((line = br.readLine()) != null) {
            sb.append(line + "\n");
        }
        br.close();
        System.out.println("" + sb.toString());
    } else {
        System.out.println(conn.getResponseMessage());
    }

如果我使用没有 JSON 消息的 HTTP Get,它可以正常工作,但如果我使用 POST 发送 JSON 消息,它会返回此错误:

java.io.IOException:服务器返回 HTTP 响应代码:400 用于 URL: https://xxxxxxx.atlassian.net/rest/api/2/issue/

我使用 Postman 应用程序 来检查标题(Content-Type 和 Authorization)和正文,并使用该应用程序在 Jira 中创建问题。

添加: 如果我检查连接,它具有参数Method,例如GET,而不是POST。

我做错了什么?

【问题讨论】:

  • 可能其他 API 只能通过 get 访问?
  • 不,因为如果我使用 Postman 应用程序进行 POST,它可以正常工作。
  • 检查回复正文。也许它可以说明问题的原因。
  • 如果我检查连接,它具有像“GET”而不是“POST”这样的请求方法如果我定义像post这样的请求怎么办?

标签: java http post jira http-status-code-400


【解决方案1】:

你能显示 400 响应的详细信息吗?

我尝试了一些关键代码并成功发出了 POST 请求。 JIRA 服务器将为 400 响应返回非常详细的消息,例如

{
    "errorMessages": [
        "Field 'priority' is required"
    ],
    "errors": {}
}

这个答案可能对如何发出帖子请求有用。 Java - sending HTTP parameters via POST method easily

【讨论】:

    【解决方案2】:

    我有一个将 Jira 集成到公司应用程序中的请求。请求是使用 OAuth,并且能够使用 Jira API,并带有重音以使用“创建问题”调用。 我稍后会提供源代码,只是为了强调使用 POST 调用时我遇到了 json 问题,我必须使用 com.google.api.client.util.GenericData 才能正确创建问题。

    代码摘录:

    @PropertySource("classpath:/JiraApiCalls/calls.properties")
    @Service
    public class JiraService {
    
        //<editor-fold desc="infra">
        @Autowired
        JiraClient jiraClient;
    
        //<editor-fold desc="Api Business Calls">
        @Value("${GET_ISSUE_BY_KEY_URL}")
        String apiCallIssueByKey;
    
        @Value("${SITE_ID_AND_PORTFOLIO_SEARCH_JQL_WITH_OR}")
        String apiCallSiteIdAndPortfolioSearchJQLWithOr;
    
        @Value("${OR_SITE_ID}")
        String apiCallOrSiteId;
    
        @Value("${SEARCH_ISSUES_URL}")
        String searchIssuesKey;
    
        @Value("${DASHBOARDS}")
        String apiCallAllDashboard;
    
        @Value("${PROJECTS}")
        String apiCallAllProjects;
    
        @Value("${PROJECT}")
        String apiCallProjectById;
    
        @Value("${ISSUETYPES}")
        String apiCallAllIssueTypes;
    
        @Value("${ISSUETYPE}")
        String apiCallApiIssueType;
    
        @Value("${ISSUE_CREATE}")
        String apiCallIssueCreate;
        //</editor-fold>
    
        //<editor-fold desc="Definitions : Jira concrete usage">
        static final List<String> ISSUE_FIELDS = Arrays.asList(
                "status", "creator", "reporter", "assignee", "description",
                "summary", "customfield_11110", "customfield_11126", "components"
        );
    
    public JiraSingleResultIssueDto getIssueByKey(String key) {
            String issueApiMethodCallUrl = MessageFormat.format( apiCallIssueByKey, key );
            JiraSingleResultIssueDto dto = jiraClient.executeGet( JiraSingleResultIssueDto.class, issueApiMethodCallUrl );
            return dto;
        }
    
        public AllDashboardsDto getAllDashboards() {
            return jiraClient.executeGet( AllDashboardsDto.class, apiCallAllDashboard );
        }
    
        public List<ProjectDto> getAllProjects() {
            List<ProjectDto> projects = jiraClient.executeGetExpectingList( apiCallAllProjects );
            return projects;
        }
    
        public ProjectDto getProjectByKey(Object key) {
            ProjectDto project = jiraClient.executeGet( ProjectDto.class, MessageFormat.format( apiCallProjectById, String.valueOf( key ) ) );
            return project;
        }
    
        public List<JiraIssueTypeDto> getAllIssueTypes() {
            List<JiraIssueTypeDto> issueTypes = jiraClient.executeGetExpectingList( apiCallAllIssueTypes );
            return issueTypes;
        }
    
        public JiraIssueTypeDto getIssueType(Object key) {
            JiraIssueTypeDto issueType = jiraClient.executeGet( JiraIssueTypeDto.class, MessageFormat.format( apiCallApiIssueType, String.valueOf( key ) ) );
            return issueType;
        }
    
        public IssueCreatedResponseDto createIssue(IssueDto issueDto) throws Exception {
            GenericData issueData = new GenericData();
    
            try {
                // check for existing Project, and carry on if it exists...
                ProjectDto projectDto = getProjectByKey( issueDto.getFields().getProject().getId() );
                GenericData projectData = new GenericData();
                projectData.put( "key", projectDto.getKey() );
    
                // check for existing issue type, and carry on with no errors..
                Long issueId = issueDto.getFields().getIssuetype().getId();
                getIssueType( issueId );
                GenericData issueTypeData = new GenericData();
                issueTypeData.put( "id", issueId );
    
                GenericData fieldsData = new GenericData();
                fieldsData.set( "summary", issueDto.getFields().getSummary() );
                fieldsData.set( "description", issueDto.getFields().getDescription() );
    
                fieldsData.set( "issuetype", issueTypeData );
                fieldsData.set( "project", projectData );
    
                issueData.put( "fields", fieldsData );
    
                IssueCreatedResponseDto issueResponse = jiraClient.executePost( IssueCreatedResponseDto.class, apiCallIssueCreate, issueData );
                return issueResponse;
            } catch (Exception e) {
                throw new Exception( e );
            }
        }
    }
    

    Jira 客户端:

    @Component
    public class JiraClient {
    
        private static Logger LOGGER = Logger.getLogger( JiraClient.class.getName() );
    
        //<editor-fold desc="oauth 1.0 credentials">
        @Value("${jira_home}")
        String JIRA_HOME_URL;
    
        @Value("${jira_base_url}")
        String JIRA_ENDPOINT_URL;
    
        @Value("${jira_access_token}")
        String JIRA_ACCESS_TOKEN;
    
        @Value("${jira_secret}")
        String JIRA_SECRET_KEY;
    
        @Value("${jira_consumer_key}")
        String JIRA_CONSUMER_KEY;
    
        @Value("${jira_private_key}")
        String JIRA_PRIVATE_KEY;
        //</editor-fold>
    
        @Value("${datetimeformat}")
        private String dateTimeFormat;
    
        JSONUtils jsonUtils;
    
        JiraOAuthClient jiraOAuthClient;
    
        @PostConstruct
        void jiraOAuthClientInit() {
            if (jiraOAuthClient == null) {
                try {
                    jiraOAuthClient = new JiraOAuthClient( JIRA_HOME_URL );
                } catch (Exception e) {
                    String errMsg = "Jira OAuth Client Error.";
                    LOGGER.log( Level.WARNING, errMsg, e );
                    throw new RuntimeException( errMsg + e );
                }
            }
    
            jsonUtils = new JSONUtils( dateTimeFormat );
        }
    
        //<editor-fold desc="Infra : Basic Get/Post Request support methods">
        public HttpResponse handleGetRequest(String apiMethodCallUrl) {
            try {
                OAuthParameters parameters = jiraOAuthClient.getParameters( JIRA_ACCESS_TOKEN, JIRA_SECRET_KEY, JIRA_CONSUMER_KEY, JIRA_PRIVATE_KEY );
                HttpResponse response = getResponseFromUrl( parameters, new GenericUrl( apiMethodCallUrl ) );
                return response;
            } catch (Exception e) {
                String errMsg = "Handle GetRequest Error.";
                LOGGER.log( Level.WARNING, errMsg, e );
                return null;
            }
        }
    
        public HttpResponse handlePostRequest(String apiMethodCallUrl, HttpContent requestContent) {
            try {
                OAuthParameters parameters = jiraOAuthClient.getParameters( JIRA_ACCESS_TOKEN, JIRA_SECRET_KEY, JIRA_CONSUMER_KEY, JIRA_PRIVATE_KEY );
                HttpResponse response = postResponseFromUrl( parameters, new GenericUrl( apiMethodCallUrl ), requestContent );
                return response;
            } catch (Exception e) {
                String errMsg = "Handle PostRequest Error.";
                LOGGER.log( Level.WARNING, errMsg, e );
                return null;
            }
        }
    
        private HttpResponse getResponseFromUrl(OAuthParameters parameters, GenericUrl jiraUrl) throws IOException {
            HttpRequestFactory requestFactory = new NetHttpTransport().createRequestFactory( parameters );
            HttpRequest request = requestFactory.buildGetRequest( jiraUrl );
            return request.execute();
        }
    
        private HttpResponse postResponseFromUrl(OAuthParameters parameters, GenericUrl jiraUrl, HttpContent requestContent) throws IOException {
            HttpRequestFactory requestFactory = new NetHttpTransport().createRequestFactory( parameters );
            HttpRequest request = requestFactory.buildPostRequest( jiraUrl, requestContent );
            return request.execute();
        }
        //</editor-fold>
    
        //<editor-fold desc="Advanced Get/Post methods">
        //<editor-fold desc="Generic universal call/response">
        private HttpResponse executeGetAndReturnHttpResponse(@NonNull String apiMethodCallUrl) {
            return handleGetRequest( JIRA_ENDPOINT_URL + apiMethodCallUrl );
        }
        //</editor-fold>
    
        /**
         * Custom GET call, expecting result of a type T<br>
         *
         * @param apiMethodCallUrl Url defined by the user.<br>
         *                         Usage example :<br>
         *                         Api call, and two parameters defined at {0} and {1} positions:<br>
         *                         SITE_ID_AND_PORTFOLIO_SEARCH_JQL_WITH_OR=Portfolio = {0} AND ("Site ID" ~ "0"{1})<br>
         *                         For proper usage, MessageFormat.format( apiCall_Name, apiCall_Parameters) may be used.<br>
         */
        public <T> T executeGet(Class<T> clazz, String apiMethodCallUrl) {
            try {
                HttpResponse jsonResponse = executeGetAndReturnHttpResponse( apiMethodCallUrl );
                if (jsonResponse == null) {
                    return null;
                }
    
                return jsonUtils.parseResponse( jsonResponse, clazz );
            } catch (Exception e) {
                String errMsg = "Executing Get Request Error.";
                LOGGER.log( Level.SEVERE, errMsg, e );
                throw new RuntimeException( errMsg, e );
            }
        }
    
        //<editor-fold desc="Default GET call with path variables injected into call, for returning Lists of objects">
    
        /**
         * Custom GET call, expecting list result.<br>
         *
         * @param apiMethodCallUrl Url defined by user.<br>
         *                         Usage example :<br>
         *                         Api call, with no parameters defined in api call "apiCallAllProjects",<br>
         *                         so there is no need for formating rest method call with parameters.<br>
         *                         If there was a need, look at {@link JiraClient#executeGet)
         */
        public <T> List<T> executeGetExpectingList(@NonNull String apiMethodCallUrl) {
            try {
                HttpResponse jsonResponse = executeGetAndReturnHttpResponse( apiMethodCallUrl );
                if (jsonResponse == null) {
                    return null;
                }
    
                return jsonUtils.parseResponseAsList( jsonResponse );
            } catch (Exception e) {
                String errMsg = "Executing Get Request Error.";
                LOGGER.log( Level.SEVERE, errMsg, e );
                throw new RuntimeException( errMsg, e );
            }
        }
        //</editor-fold>
    
        //<editor-fold desc="POST">
        public HttpResponse executePostRequest(@NonNull String postOperationName, @NonNull GenericData contentGenericData) {
            String apiCallUrlPath = JIRA_ENDPOINT_URL + postOperationName;
    
            try {
                OAuthParameters parameters = jiraOAuthClient.getParameters( JIRA_ACCESS_TOKEN, JIRA_SECRET_KEY, JIRA_CONSUMER_KEY, JIRA_PRIVATE_KEY );
                HttpContent content = new JsonHttpContent( new JacksonFactory(), contentGenericData );
                HttpResponse response = postResponseFromUrl( parameters, new GenericUrl( apiCallUrlPath ), content );
    
                return response;
            } catch (HttpResponseException hre) {
                String errMsg = "Executing Post Request Error. " + hre;
                LOGGER.log( Level.SEVERE, errMsg, hre );
                throw new RuntimeException( errMsg, hre );
            } catch (Exception e) {
                String errMsg = "Executing Get Request, no result.";
                LOGGER.log( Level.INFO, errMsg, e );
                throw new RuntimeException( errMsg, e );
            }
        }
    
        public <T> T executePost(Class<T> clazz, @NonNull String postOperationName, @NonNull GenericData contentGenericData) {
            try {
                HttpResponse jsonResponse = executePostRequest( postOperationName, contentGenericData );
                if (jsonResponse == null) {
                    return null;
                }
    
                return jsonUtils.parseResponse( jsonResponse, clazz );
            } catch (Exception e) {
                String errMsg = "Executing Post Request Error.";
                LOGGER.log( Level.WARNING, errMsg, e );
                throw new RuntimeException( errMsg, e );
            }
        }
        //</editor-fold>
        //</editor-fold>
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-05-17
      • 1970-01-01
      • 2019-05-28
      • 2016-07-12
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多