diff --git a/pom.xml b/pom.xml index b8138797e4..5b11e2f88c 100644 --- a/pom.xml +++ b/pom.xml @@ -7,7 +7,7 @@ github-api - 1.92 + 1.93 GitHub API for Java http://github-api.kohsuke.org/ GitHub API for Java @@ -16,7 +16,7 @@ scm:git:git@github.com/kohsuke/${project.artifactId}.git scm:git:ssh://git@github.com/kohsuke/${project.artifactId}.git http://${project.artifactId}.kohsuke.org/ - github-api-1.92 + github-api-1.93 @@ -96,9 +96,9 @@ - commons-lang - commons-lang - 2.6 + org.apache.commons + commons-lang3 + 3.7 commons-codec diff --git a/src/main/java/org/kohsuke/github/GHCommentAuthorAssociation.java b/src/main/java/org/kohsuke/github/GHCommentAuthorAssociation.java new file mode 100644 index 0000000000..d66b8d8550 --- /dev/null +++ b/src/main/java/org/kohsuke/github/GHCommentAuthorAssociation.java @@ -0,0 +1,37 @@ +package org.kohsuke.github; + +/** + * How is an user associated with a repository? + * + * @author Kohsuke Kawaguchi + */ +public enum GHCommentAuthorAssociation { + /** + * Author has been invited to collaborate on the repository. + */ + COLLABORATOR, + /** + * Author has previously committed to the repository. + */ + CONTRIBUTOR, + /** + * Author has not previously committed to GitHub. + */ + FIRST_TIMER, + /** + * Author has not previously committed to the repository. + */ + FIRST_TIME_CONTRIBUTOR, + /** + * Author is a member of the organization that owns the repository. + */ + MEMBER, + /** + * Author has no association with the repository. + */ + NONE, + /** + * Author is the owner of the repository. + */ + OWNER +} diff --git a/src/main/java/org/kohsuke/github/GHCommitSearchBuilder.java b/src/main/java/org/kohsuke/github/GHCommitSearchBuilder.java index 23960528f2..3d29aa80fd 100644 --- a/src/main/java/org/kohsuke/github/GHCommitSearchBuilder.java +++ b/src/main/java/org/kohsuke/github/GHCommitSearchBuilder.java @@ -1,6 +1,6 @@ package org.kohsuke.github; -import org.apache.commons.lang.StringUtils; +import org.apache.commons.lang3.StringUtils; import java.io.IOException; diff --git a/src/main/java/org/kohsuke/github/GHDeployKey.java b/src/main/java/org/kohsuke/github/GHDeployKey.java index bfa03b2508..04acda8022 100644 --- a/src/main/java/org/kohsuke/github/GHDeployKey.java +++ b/src/main/java/org/kohsuke/github/GHDeployKey.java @@ -1,6 +1,6 @@ package org.kohsuke.github; -import org.apache.commons.lang.builder.ToStringBuilder; +import org.apache.commons.lang3.builder.ToStringBuilder; import java.io.IOException; diff --git a/src/main/java/org/kohsuke/github/GHIssue.java b/src/main/java/org/kohsuke/github/GHIssue.java index 186ea16719..f7cfd9245c 100644 --- a/src/main/java/org/kohsuke/github/GHIssue.java +++ b/src/main/java/org/kohsuke/github/GHIssue.java @@ -29,7 +29,6 @@ import java.io.IOException; import java.net.URL; -import java.util.ArrayList; import java.util.Arrays; import java.util.Collection; import java.util.Collections; @@ -49,6 +48,8 @@ * @see GHIssueSearchBuilder */ public class GHIssue extends GHObject implements Reactable{ + private static final String ASSIGNEES = "assignees"; + GitHub root; GHRepository owner; @@ -268,8 +269,7 @@ public void addAssignees(GHUser... assignees) throws IOException { } public void addAssignees(Collection assignees) throws IOException { - List names = toLogins(assignees); - root.retrieve().method("POST").with("assignees",names).to(getIssuesApiRoute()+"/assignees",this); + root.retrieve().method("POST").withLogins(ASSIGNEES,assignees).to(getIssuesApiRoute()+"/assignees",this); } public void setAssignees(GHUser... assignees) throws IOException { @@ -277,7 +277,7 @@ public void setAssignees(GHUser... assignees) throws IOException { } public void setAssignees(Collection assignees) throws IOException { - editIssue("assignees",toLogins(assignees)); + new Requester(root).withLogins(ASSIGNEES, assignees).method("PATCH").to(getIssuesApiRoute()); } public void removeAssignees(GHUser... assignees) throws IOException { @@ -285,16 +285,7 @@ public void removeAssignees(GHUser... assignees) throws IOException { } public void removeAssignees(Collection assignees) throws IOException { - List names = toLogins(assignees); - root.retrieve().method("DELETE").with("assignees",names).inBody().to(getIssuesApiRoute()+"/assignees",this); - } - - private List toLogins(Collection assignees) { - List names = new ArrayList(assignees.size()); - for (GHUser a : assignees) { - names.add(a.getLogin()); - } - return names; + root.retrieve().method("DELETE").withLogins(ASSIGNEES,assignees).inBody().to(getIssuesApiRoute()+"/assignees",this); } protected String getApiRoute() { diff --git a/src/main/java/org/kohsuke/github/GHIssueComment.java b/src/main/java/org/kohsuke/github/GHIssueComment.java index 3f4d70643d..1b7eea5ebc 100644 --- a/src/main/java/org/kohsuke/github/GHIssueComment.java +++ b/src/main/java/org/kohsuke/github/GHIssueComment.java @@ -32,11 +32,13 @@ * Comment to the issue * * @author Kohsuke Kawaguchi + * @see GHIssue#comment(String) + * @see GHIssue#listComments() */ public class GHIssueComment extends GHObject implements Reactable { GHIssue owner; - private String body, gravatar_id; + private String body, gravatar_id, html_url, author_association; private GHUser user; // not fully populated. beware. /*package*/ GHIssueComment wrapUp(GHIssue owner) { @@ -73,12 +75,13 @@ public GHUser getUser() throws IOException { return owner == null || owner.root.isOffline() ? user : owner.root.getUser(user.getLogin()); } - /** - * @deprecated This object has no HTML URL. - */ @Override public URL getHtmlUrl() { - return null; + return GitHub.parseURL(html_url); + } + + public GHCommentAuthorAssociation getAuthorAssociation() { + return GHCommentAuthorAssociation.valueOf(author_association); } /** diff --git a/src/main/java/org/kohsuke/github/GHKey.java b/src/main/java/org/kohsuke/github/GHKey.java index 63ab7b3ff9..d4c8197dbf 100644 --- a/src/main/java/org/kohsuke/github/GHKey.java +++ b/src/main/java/org/kohsuke/github/GHKey.java @@ -1,7 +1,7 @@ package org.kohsuke.github; import edu.umd.cs.findbugs.annotations.SuppressFBWarnings; -import org.apache.commons.lang.builder.ToStringBuilder; +import org.apache.commons.lang3.builder.ToStringBuilder; /** * SSH public key. diff --git a/src/main/java/org/kohsuke/github/GHObject.java b/src/main/java/org/kohsuke/github/GHObject.java index 3b26ed77cc..2bad0891bc 100644 --- a/src/main/java/org/kohsuke/github/GHObject.java +++ b/src/main/java/org/kohsuke/github/GHObject.java @@ -2,8 +2,8 @@ import com.infradna.tool.bridge_method_injector.WithBridgeMethods; import edu.umd.cs.findbugs.annotations.SuppressFBWarnings; -import org.apache.commons.lang.builder.ReflectionToStringBuilder; -import org.apache.commons.lang.builder.ToStringStyle; +import org.apache.commons.lang3.builder.ReflectionToStringBuilder; +import org.apache.commons.lang3.builder.ToStringStyle; import javax.annotation.CheckForNull; import java.io.IOException; diff --git a/src/main/java/org/kohsuke/github/GHPullRequest.java b/src/main/java/org/kohsuke/github/GHPullRequest.java index b5f02b964c..16c3f953c6 100644 --- a/src/main/java/org/kohsuke/github/GHPullRequest.java +++ b/src/main/java/org/kohsuke/github/GHPullRequest.java @@ -41,6 +41,7 @@ public class GHPullRequest extends GHIssue { private static final String COMMENTS_ACTION = "/comments"; + private static final String REQUEST_REVIEWERS = "/requested_reviewers"; private String patch_url, diff_url, issue_url; private GHCommitPointer base; @@ -345,6 +346,12 @@ public GHPullRequestReviewComment createReviewComment(String body, String sha, S .to(getApiRoute() + COMMENTS_ACTION, GHPullRequestReviewComment.class).wrapUp(this); } + public void requestReviewers(List reviewers) throws IOException { + new Requester(root).method("POST") + .withLogins("reviewers", reviewers) + .to(getApiRoute() + REQUEST_REVIEWERS); + } + /** * Merge this pull request. * @@ -393,7 +400,7 @@ public enum MergeMethod{ MERGE, SQUASH, REBASE } private void fetchIssue() throws IOException { if (!fetchedIssueDetails) { - new Requester(root).to(getIssuesApiRoute(), this); + new Requester(root).method("GET").to(getIssuesApiRoute(), this); fetchedIssueDetails = true; } } diff --git a/src/main/java/org/kohsuke/github/GHPullRequestFileDetail.java b/src/main/java/org/kohsuke/github/GHPullRequestFileDetail.java index 1ee55d37cc..35bb86c444 100644 --- a/src/main/java/org/kohsuke/github/GHPullRequestFileDetail.java +++ b/src/main/java/org/kohsuke/github/GHPullRequestFileDetail.java @@ -43,6 +43,7 @@ public class GHPullRequestFileDetail { String raw_url; String contents_url; String patch; + String previous_filename; public String getSha() { return sha; @@ -83,4 +84,9 @@ public URL getContentsUrl() { public String getPatch() { return patch; } + + public String getPreviousFilename() + { + return previous_filename; + } } diff --git a/src/main/java/org/kohsuke/github/GHRepository.java b/src/main/java/org/kohsuke/github/GHRepository.java index b40f387b7f..3c80c499ff 100644 --- a/src/main/java/org/kohsuke/github/GHRepository.java +++ b/src/main/java/org/kohsuke/github/GHRepository.java @@ -27,7 +27,7 @@ import com.infradna.tool.bridge_method_injector.WithBridgeMethods; import edu.umd.cs.findbugs.annotations.SuppressFBWarnings; import org.apache.commons.codec.binary.Base64; -import org.apache.commons.lang.StringUtils; +import org.apache.commons.lang3.StringUtils; import java.io.FileNotFoundException; import java.io.IOException; diff --git a/src/main/java/org/kohsuke/github/GHSearchBuilder.java b/src/main/java/org/kohsuke/github/GHSearchBuilder.java index 17c2db85b8..44521687f4 100644 --- a/src/main/java/org/kohsuke/github/GHSearchBuilder.java +++ b/src/main/java/org/kohsuke/github/GHSearchBuilder.java @@ -1,6 +1,6 @@ package org.kohsuke.github; -import org.apache.commons.lang.StringUtils; +import org.apache.commons.lang3.StringUtils; import java.util.ArrayList; import java.util.List; diff --git a/src/main/java/org/kohsuke/github/GitHub.java b/src/main/java/org/kohsuke/github/GitHub.java index f7e0d58096..52a16906da 100644 --- a/src/main/java/org/kohsuke/github/GitHub.java +++ b/src/main/java/org/kohsuke/github/GitHub.java @@ -24,6 +24,7 @@ package org.kohsuke.github; import com.fasterxml.jackson.databind.DeserializationFeature; +import com.fasterxml.jackson.databind.MapperFeature; import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.databind.introspect.VisibilityChecker.Std; import com.infradna.tool.bridge_method_injector.WithBridgeMethods; @@ -909,6 +910,7 @@ public Reader renderMarkdown(String text) throws IOException { static { MAPPER.setVisibilityChecker(new Std(NONE, NONE, NONE, NONE, ANY)); MAPPER.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false); + MAPPER.configure(MapperFeature.ACCEPT_CASE_INSENSITIVE_ENUMS, true); } /* package */ static final String GITHUB_URL = "https://api.github.com"; diff --git a/src/main/java/org/kohsuke/github/Requester.java b/src/main/java/org/kohsuke/github/Requester.java index 899597b33e..4670e311e5 100644 --- a/src/main/java/org/kohsuke/github/Requester.java +++ b/src/main/java/org/kohsuke/github/Requester.java @@ -26,7 +26,7 @@ import com.fasterxml.jackson.databind.JsonMappingException; import edu.umd.cs.findbugs.annotations.SuppressFBWarnings; import org.apache.commons.io.IOUtils; -import org.apache.commons.lang.StringUtils; +import org.apache.commons.lang3.StringUtils; import javax.annotation.CheckForNull; import javax.annotation.WillClose; @@ -63,7 +63,7 @@ import static java.util.logging.Level.FINE; import static java.util.logging.Level.FINEST; import static java.util.logging.Level.INFO; -import static org.apache.commons.lang.StringUtils.defaultString; +import static org.apache.commons.lang3.StringUtils.defaultString; import static org.kohsuke.github.GitHub.MAPPER; /** @@ -169,6 +169,14 @@ public Requester with(String key, Collection value) { return _with(key, value); } + public Requester withLogins(String key, Collection users) { + List names = new ArrayList(users.size()); + for (GHUser a : users) { + names.add(a.getLogin()); + } + return with(key,names); + } + public Requester with(String key, Map value) { return _with(key, value); } diff --git a/src/main/java/org/kohsuke/github/extras/OkHttpConnector.java b/src/main/java/org/kohsuke/github/extras/OkHttpConnector.java index faa06b0d3b..e7802c6bae 100644 --- a/src/main/java/org/kohsuke/github/extras/OkHttpConnector.java +++ b/src/main/java/org/kohsuke/github/extras/OkHttpConnector.java @@ -1,13 +1,25 @@ package org.kohsuke.github.extras; +import com.squareup.okhttp.ConnectionSpec; import com.squareup.okhttp.OkHttpClient; import com.squareup.okhttp.OkUrlFactory; + import org.kohsuke.github.HttpConnector; import java.io.IOException; + import java.net.HttpURLConnection; import java.net.URL; +import java.security.KeyManagementException; +import java.security.NoSuchAlgorithmException; + +import java.util.Arrays; +import java.util.List; + +import javax.net.ssl.SSLContext; +import javax.net.ssl.SSLSocketFactory; + /** * {@link HttpConnector} for {@link OkHttpClient}. * @@ -23,10 +35,33 @@ public class OkHttpConnector implements HttpConnector { private final OkUrlFactory urlFactory; public OkHttpConnector(OkUrlFactory urlFactory) { + urlFactory.client().setSslSocketFactory(TlsSocketFactory()); + urlFactory.client().setConnectionSpecs(TlsConnectionSpecs()); this.urlFactory = urlFactory; } public HttpURLConnection connect(URL url) throws IOException { return urlFactory.open(url); } + + /** Returns TLSv1.2 only SSL Socket Factory. */ + private SSLSocketFactory TlsSocketFactory() { + SSLContext sc; + try { + sc = SSLContext.getInstance("TLSv1.2"); + } catch (NoSuchAlgorithmException e) { + throw new RuntimeException(e.getMessage(), e); + } + try { + sc.init(null, null, null); + return sc.getSocketFactory(); + } catch (KeyManagementException e) { + throw new RuntimeException(e.getMessage(), e); + } + } + + /** Returns connection spec with TLS v1.2 in it */ + private List TlsConnectionSpecs() { + return Arrays.asList(ConnectionSpec.MODERN_TLS, ConnectionSpec.CLEARTEXT); + } } diff --git a/src/test/java/org/kohsuke/github/AppTest.java b/src/test/java/org/kohsuke/github/AppTest.java index e069a74edb..807e8ca7c6 100755 --- a/src/test/java/org/kohsuke/github/AppTest.java +++ b/src/test/java/org/kohsuke/github/AppTest.java @@ -304,7 +304,7 @@ public void testGetTeamsForRepo() throws Exception { @Test public void testMembership() throws Exception { - Set members = gitHub.getOrganization("jenkinsci").getRepository("violations-plugin").getCollaboratorNames(); + Set members = gitHub.getOrganization("github-api-test-org").getRepository("jenkins").getCollaboratorNames(); System.out.println(members.contains("kohsuke")); }