Pure Java REST API POST calls to Jenkins /reload o

2019-08-21 01:56发布

问题:

I'm getting an Exception when running this, but Jenkins actually executes the requested action:

  URL url = new URL("https://somehost.com/jenkins/quietDown");
  HttpURLConnection c= (HttpURLConnection) url.openConnection();
  c.setRequestMethod("POST");
  c.setRequestProperty("Authorization", "Basic " + Base64.getEncoder().encodeToString(("user:apiToken").getBytes()));
  c.getInputStream().close();

Exception:

Exception in thread "main" java.io.IOException: Server returned HTTP response code: 403 for URL: https://somehost.com/jenkins/
    at sun.net.www.protocol.http.HttpURLConnection.getInputStream0(HttpURLConnection.java:1894)
    at sun.net.www.protocol.http.HttpURLConnection.getInputStream(HttpURLConnection.java:1492)
    at sun.net.www.protocol.https.HttpsURLConnectionImpl.getInputStream(HttpsURLConnectionImpl.java:263)
    at build.JenkinsClient.main(JenkinsClient.java:102)

Testing with Jenkins 2.164.3 and Java 8.

回答1:

Setting this gets rid of the Exception:

connection.setInstanceFollowRedirects(false);

After hours I noticed how the stack trace contained a slightly different URL than the one I was posting to:

https://somehost.com/jenkins/
vs
https://somehost.com/jenkins/quietDown

It seems like Jenkins answers with a redirect (302 Found), which the HttUrlConnections follows by default to read from, which then for some reason caused that exception.

For the longest time, I tried to figure out a way to issue the POST request without calling connection.getInputStream(), but that seems to be the only call which actually triggers the request. If anyone knows a different way to issue a POST request with pure Java, please let me know.

I knew my URL and username:token stuff was correct because I tested with curl (which doesn't complain, even with the follow redirect option turned on):

curl -X POST https://somehost.com/jenkins/quietDown -u admin:token
curl -L -X POST https://somehost.com/jenkins/quietDown -u admin:token