mirror of
https://github.com/jlengrand/github-api.git
synced 2026-03-11 15:50:17 +00:00
Compare commits
63 Commits
github-api
...
github-api
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
55e218ac37 | ||
|
|
7d1f636cdd | ||
|
|
a4b8b9b09b | ||
|
|
4e8e28d27c | ||
|
|
4b52414435 | ||
|
|
811b96bcbe | ||
|
|
f3207855ca | ||
|
|
9f3c5b93e3 | ||
|
|
a56357f0c1 | ||
|
|
f8d14d2e56 | ||
|
|
b0c30759c8 | ||
|
|
54037e6e10 | ||
|
|
fc260d4a37 | ||
|
|
387d4e5bc9 | ||
|
|
4ffd46b391 | ||
|
|
3b49370c06 | ||
|
|
925d26e54c | ||
|
|
1283006b53 | ||
|
|
83a718c9db | ||
|
|
2abf03ccb7 | ||
|
|
a59810a487 | ||
|
|
9cc9e06ad1 | ||
|
|
0108a0c146 | ||
|
|
4188758d84 | ||
|
|
2144100f81 | ||
|
|
8a61e04be6 | ||
|
|
eaeb083891 | ||
|
|
25e117b412 | ||
|
|
6b7ceed1a5 | ||
|
|
0533fc98a2 | ||
|
|
edde3ab2fb | ||
|
|
ec20e518be | ||
|
|
930a582afa | ||
|
|
7536eeea54 | ||
|
|
d940d43907 | ||
|
|
3ad3dd9493 | ||
|
|
553df7ac85 | ||
|
|
9648602252 | ||
|
|
63d0d13330 | ||
|
|
ff9b538a49 | ||
|
|
6632da34c0 | ||
|
|
178c9ff4d0 | ||
|
|
bfefeae5c1 | ||
|
|
ebf953cbc4 | ||
|
|
19ec3321ae | ||
|
|
d82af9f1a0 | ||
|
|
4712d2c8ac | ||
|
|
a2df4217fd | ||
|
|
096c96550b | ||
|
|
2fb3f31930 | ||
|
|
f52b4a2e11 | ||
|
|
bbc78ffec6 | ||
|
|
3606f412b3 | ||
|
|
6e0e94094b | ||
|
|
976960f495 | ||
|
|
d2f2f3b2d3 | ||
|
|
2da7c45840 | ||
|
|
fb078de627 | ||
|
|
da46b7fddb | ||
|
|
c4e0729b7d | ||
|
|
eee9f0ace5 | ||
|
|
d0692458a3 | ||
|
|
c96e6c7c92 |
27
pom.xml
27
pom.xml
@@ -7,7 +7,7 @@
|
|||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<artifactId>github-api</artifactId>
|
<artifactId>github-api</artifactId>
|
||||||
<version>1.43</version>
|
<version>1.48</version>
|
||||||
<name>GitHub API for Java</name>
|
<name>GitHub API for Java</name>
|
||||||
<url>http://github-api.kohsuke.org/</url>
|
<url>http://github-api.kohsuke.org/</url>
|
||||||
<description>GitHub API for Java</description>
|
<description>GitHub API for Java</description>
|
||||||
@@ -16,6 +16,7 @@
|
|||||||
<connection>scm:git:git@github.com/kohsuke/${project.artifactId}.git</connection>
|
<connection>scm:git:git@github.com/kohsuke/${project.artifactId}.git</connection>
|
||||||
<developerConnection>scm:git:ssh://git@github.com/kohsuke/${project.artifactId}.git</developerConnection>
|
<developerConnection>scm:git:ssh://git@github.com/kohsuke/${project.artifactId}.git</developerConnection>
|
||||||
<url>http://${project.artifactId}.kohsuke.org/</url>
|
<url>http://${project.artifactId}.kohsuke.org/</url>
|
||||||
|
<tag>github-api-1.48</tag>
|
||||||
</scm>
|
</scm>
|
||||||
|
|
||||||
<distributionManagement>
|
<distributionManagement>
|
||||||
@@ -34,7 +35,7 @@
|
|||||||
<plugin>
|
<plugin>
|
||||||
<groupId>com.infradna.tool</groupId>
|
<groupId>com.infradna.tool</groupId>
|
||||||
<artifactId>bridge-method-injector</artifactId>
|
<artifactId>bridge-method-injector</artifactId>
|
||||||
<version>1.2</version>
|
<version>1.8</version>
|
||||||
<executions>
|
<executions>
|
||||||
<execution>
|
<execution>
|
||||||
<goals>
|
<goals>
|
||||||
@@ -64,9 +65,9 @@
|
|||||||
<scope>test</scope>
|
<scope>test</scope>
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.codehaus.jackson</groupId>
|
<groupId>com.fasterxml.jackson.core</groupId>
|
||||||
<artifactId>jackson-mapper-asl</artifactId>
|
<artifactId>jackson-databind</artifactId>
|
||||||
<version>1.9.9</version>
|
<version>2.2.3</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>commons-io</groupId>
|
<groupId>commons-io</groupId>
|
||||||
@@ -76,7 +77,7 @@
|
|||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.infradna.tool</groupId>
|
<groupId>com.infradna.tool</groupId>
|
||||||
<artifactId>bridge-method-annotation</artifactId>
|
<artifactId>bridge-method-annotation</artifactId>
|
||||||
<version>1.4</version>
|
<version>1.8</version>
|
||||||
<optional>true</optional>
|
<optional>true</optional>
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
@@ -85,14 +86,25 @@
|
|||||||
<version>1.1</version>
|
<version>1.1</version>
|
||||||
<scope>test</scope>
|
<scope>test</scope>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.eclipse.jgit</groupId>
|
||||||
|
<artifactId>org.eclipse.jgit</artifactId>
|
||||||
|
<version>3.1.0.201310021548-r</version>
|
||||||
|
<scope>test</scope>
|
||||||
|
</dependency>
|
||||||
</dependencies>
|
</dependencies>
|
||||||
|
|
||||||
<repositories>
|
<repositories>
|
||||||
<repository>
|
<repository>
|
||||||
<id>repo.jenkins-ci.org</id>
|
<id>repo.jenkins-ci.org</id>
|
||||||
<url>http://repo.jenkins-ci.org/public/</url>
|
<url>http://repo.jenkins-ci.org/public/</url>
|
||||||
</repository>
|
</repository>
|
||||||
</repositories>
|
</repositories>
|
||||||
|
<pluginRepositories>
|
||||||
|
<pluginRepository>
|
||||||
|
<id>repo.jenkins-ci.org</id>
|
||||||
|
<url>http://repo.jenkins-ci.org/public/</url>
|
||||||
|
</pluginRepository>
|
||||||
|
</pluginRepositories>
|
||||||
|
|
||||||
<reporting>
|
<reporting>
|
||||||
<plugins>
|
<plugins>
|
||||||
@@ -102,4 +114,5 @@
|
|||||||
</plugin>
|
</plugin>
|
||||||
</plugins>
|
</plugins>
|
||||||
</reporting>
|
</reporting>
|
||||||
|
|
||||||
</project>
|
</project>
|
||||||
|
|||||||
108
src/main/java/org/kohsuke/github/GHAsset.java
Normal file
108
src/main/java/org/kohsuke/github/GHAsset.java
Normal file
@@ -0,0 +1,108 @@
|
|||||||
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Asset in a release.
|
||||||
|
*
|
||||||
|
* @see GHRelease#getAssets()
|
||||||
|
*/
|
||||||
|
public class GHAsset {
|
||||||
|
GitHub root;
|
||||||
|
GHRepository owner;
|
||||||
|
private String url;
|
||||||
|
private String id;
|
||||||
|
private String name;
|
||||||
|
private String label;
|
||||||
|
private String state;
|
||||||
|
private String content_type;
|
||||||
|
private long size;
|
||||||
|
private long download_count;
|
||||||
|
private Date created_at;
|
||||||
|
private Date updated_at;
|
||||||
|
|
||||||
|
public String getContentType() {
|
||||||
|
return content_type;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setContentType(String contentType) throws IOException {
|
||||||
|
edit("content_type", contentType);
|
||||||
|
this.content_type = contentType;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Date getCreatedAt() {
|
||||||
|
return created_at;
|
||||||
|
}
|
||||||
|
|
||||||
|
public long getDownloadCount() {
|
||||||
|
return download_count;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getId() {
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getLabel() {
|
||||||
|
return label;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setLabel(String label) throws IOException {
|
||||||
|
edit("label", label);
|
||||||
|
this.label = label;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHRepository getOwner() {
|
||||||
|
return owner;
|
||||||
|
}
|
||||||
|
|
||||||
|
public GitHub getRoot() {
|
||||||
|
return root;
|
||||||
|
}
|
||||||
|
|
||||||
|
public long getSize() {
|
||||||
|
return size;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getState() {
|
||||||
|
return state;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Date getUpdatedAt() {
|
||||||
|
return updated_at;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getUrl() {
|
||||||
|
return url;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void edit(String key, Object value) throws IOException {
|
||||||
|
new Requester(root)._with(key, value).method("PATCH").to(getApiRoute());
|
||||||
|
}
|
||||||
|
|
||||||
|
public void delete() throws IOException {
|
||||||
|
new Requester(root).method("DELETE").to(getApiRoute());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private String getApiRoute() {
|
||||||
|
return "/repos/" + owner.getOwnerName() + "/" + owner.getName() + "/releases/assets/" + id;
|
||||||
|
}
|
||||||
|
|
||||||
|
GHAsset wrap(GHRelease release) {
|
||||||
|
this.owner = release.getOwner();
|
||||||
|
this.root = owner.root;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static GHAsset[] wrap(GHAsset[] assets, GHRelease release) {
|
||||||
|
for (GHAsset aTo : assets) {
|
||||||
|
aTo.wrap(release);
|
||||||
|
}
|
||||||
|
return assets;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,5 +1,7 @@
|
|||||||
package org.kohsuke.github;
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
import com.infradna.tool.bridge_method_injector.WithBridgeMethods;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
import java.util.AbstractList;
|
import java.util.AbstractList;
|
||||||
@@ -16,6 +18,47 @@ import java.util.List;
|
|||||||
*/
|
*/
|
||||||
public class GHCommit {
|
public class GHCommit {
|
||||||
private GHRepository owner;
|
private GHRepository owner;
|
||||||
|
|
||||||
|
private ShortInfo commit;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Short summary of this commit.
|
||||||
|
*/
|
||||||
|
public static class ShortInfo {
|
||||||
|
private GHAuthor author;
|
||||||
|
private GHAuthor committer;
|
||||||
|
|
||||||
|
private String message;
|
||||||
|
|
||||||
|
private int comment_count;
|
||||||
|
|
||||||
|
@WithBridgeMethods(value=GHAuthor.class,castRequired=true)
|
||||||
|
public GitUser getAuthor() {
|
||||||
|
return author;
|
||||||
|
}
|
||||||
|
|
||||||
|
@WithBridgeMethods(value=GHAuthor.class,castRequired=true)
|
||||||
|
public GitUser getCommitter() {
|
||||||
|
return committer;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Commit message.
|
||||||
|
*/
|
||||||
|
public String getMessage() {
|
||||||
|
return message;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getCommentCount() {
|
||||||
|
return comment_count;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @deprecated Use {@link GitUser} instead.
|
||||||
|
*/
|
||||||
|
public static class GHAuthor extends GitUser {
|
||||||
|
}
|
||||||
|
|
||||||
public static class Stats {
|
public static class Stats {
|
||||||
int total,additions,deletions;
|
int total,additions,deletions;
|
||||||
@@ -110,8 +153,14 @@ public class GHCommit {
|
|||||||
Stats stats;
|
Stats stats;
|
||||||
List<Parent> parents;
|
List<Parent> parents;
|
||||||
User author,committer;
|
User author,committer;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
public ShortInfo getCommitShortInfo() {
|
||||||
|
return commit;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
* The repository that contains the commit.
|
* The repository that contains the commit.
|
||||||
*/
|
*/
|
||||||
public GHRepository getOwner() {
|
public GHRepository getOwner() {
|
||||||
|
|||||||
@@ -31,11 +31,11 @@ package org.kohsuke.github;
|
|||||||
public class GHCommitPointer {
|
public class GHCommitPointer {
|
||||||
private String ref, sha, label;
|
private String ref, sha, label;
|
||||||
private GHUser user;
|
private GHUser user;
|
||||||
private GHRepository repository/*V2*/,repo/*V3*/;
|
private GHRepository repo;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This points to the user who owns
|
* This points to the user who owns
|
||||||
* the {@link #repository}.
|
* the {@link #getRepository()}.
|
||||||
*/
|
*/
|
||||||
public GHUser getUser() {
|
public GHUser getUser() {
|
||||||
return user;
|
return user;
|
||||||
@@ -45,7 +45,7 @@ public class GHCommitPointer {
|
|||||||
* The repository that contains the commit.
|
* The repository that contains the commit.
|
||||||
*/
|
*/
|
||||||
public GHRepository getRepository() {
|
public GHRepository getRepository() {
|
||||||
return repo!=null ? repo : repository;
|
return repo;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -72,6 +72,5 @@ public class GHCommitPointer {
|
|||||||
void wrapUp(GitHub root) {
|
void wrapUp(GitHub root) {
|
||||||
if (user!=null) user.root = root;
|
if (user!=null) user.root = root;
|
||||||
if (repo!=null) repo.wrap(root);
|
if (repo!=null) repo.wrap(root);
|
||||||
if (repository!=null) repository.wrap(root);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,7 @@
|
|||||||
package org.kohsuke.github;
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
import com.infradna.tool.bridge_method_injector.WithBridgeMethods;
|
||||||
|
|
||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
|
|
||||||
@@ -109,11 +111,13 @@ public class GHCompare {
|
|||||||
return message;
|
return message;
|
||||||
}
|
}
|
||||||
|
|
||||||
public User getAuthor() {
|
@WithBridgeMethods(value=User.class,castRequired=true)
|
||||||
|
public GitUser getAuthor() {
|
||||||
return author;
|
return author;
|
||||||
}
|
}
|
||||||
|
|
||||||
public User getCommitter() {
|
@WithBridgeMethods(value=User.class,castRequired=true)
|
||||||
|
public GitUser getCommitter() {
|
||||||
return committer;
|
return committer;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -134,23 +138,13 @@ public class GHCompare {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class User {
|
/**
|
||||||
private String name, email, date;
|
* @deprecated use {@link GitUser} instead.
|
||||||
|
*/
|
||||||
public String getName() {
|
public static class User extends GitUser {
|
||||||
return name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getEmail() {
|
|
||||||
return email;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Date getDate() {
|
|
||||||
return GitHub.parseDate(date);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static enum Status {
|
public static enum Status {
|
||||||
behind, ahead, identical;
|
behind, ahead, identical
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
171
src/main/java/org/kohsuke/github/GHContent.java
Normal file
171
src/main/java/org/kohsuke/github/GHContent.java
Normal file
@@ -0,0 +1,171 @@
|
|||||||
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import javax.xml.bind.DatatypeConverter;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A Content of a repository.
|
||||||
|
*
|
||||||
|
* @author Alexandre COLLIGNON
|
||||||
|
*/
|
||||||
|
public final class GHContent {
|
||||||
|
private GHRepository owner;
|
||||||
|
|
||||||
|
private String type;
|
||||||
|
private String encoding;
|
||||||
|
private long size;
|
||||||
|
private String sha;
|
||||||
|
private String name;
|
||||||
|
private String path;
|
||||||
|
private String content;
|
||||||
|
private String url; // this is the API url
|
||||||
|
private String git_url; // this is the Blob url
|
||||||
|
private String html_url; // this is the UI
|
||||||
|
|
||||||
|
public GHRepository getOwner() {
|
||||||
|
return owner;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getType() {
|
||||||
|
return type;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getEncoding() {
|
||||||
|
return encoding;
|
||||||
|
}
|
||||||
|
|
||||||
|
public long getSize() {
|
||||||
|
return size;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getSha() {
|
||||||
|
return sha;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getPath() {
|
||||||
|
return path;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retrieve the decoded content that is stored at this location.
|
||||||
|
*
|
||||||
|
* Due to the nature of GitHub's API, you're not guaranteed that
|
||||||
|
* the content will already be populated, so this may trigger
|
||||||
|
* network activity, and can throw an IOException.
|
||||||
|
**/
|
||||||
|
public String getContent() throws IOException {
|
||||||
|
return new String(DatatypeConverter.parseBase64Binary(getEncodedContent()));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retrieve the raw content that is stored at this location.
|
||||||
|
*
|
||||||
|
* Due to the nature of GitHub's API, you're not guaranteed that
|
||||||
|
* the content will already be populated, so this may trigger
|
||||||
|
* network activity, and can throw an IOException.
|
||||||
|
**/
|
||||||
|
public String getEncodedContent() throws IOException {
|
||||||
|
if (content != null)
|
||||||
|
return content;
|
||||||
|
|
||||||
|
GHContent retrievedContent = owner.getFileContent(path);
|
||||||
|
|
||||||
|
this.size = retrievedContent.size;
|
||||||
|
this.sha = retrievedContent.sha;
|
||||||
|
this.content = retrievedContent.content;
|
||||||
|
this.url = retrievedContent.url;
|
||||||
|
this.git_url = retrievedContent.git_url;
|
||||||
|
this.html_url = retrievedContent.html_url;
|
||||||
|
|
||||||
|
return content;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getUrl() {
|
||||||
|
return url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getGitUrl() {
|
||||||
|
return git_url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getHtmlUrl() {
|
||||||
|
return html_url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isFile() {
|
||||||
|
return "file".equals(type);
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isDirectory() {
|
||||||
|
return "dir".equals(type);
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHContentUpdateResponse update(String newContent, String commitMessage) throws IOException {
|
||||||
|
return update(newContent, commitMessage, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHContentUpdateResponse update(String newContent, String commitMessage, String branch) throws IOException {
|
||||||
|
String encodedContent = DatatypeConverter.printBase64Binary(newContent.getBytes());
|
||||||
|
|
||||||
|
Requester requester = new Requester(owner.root)
|
||||||
|
.with("path", path)
|
||||||
|
.with("message", commitMessage)
|
||||||
|
.with("sha", sha)
|
||||||
|
.with("content", encodedContent)
|
||||||
|
.method("PUT");
|
||||||
|
|
||||||
|
if (branch != null) {
|
||||||
|
requester.with("branch", branch);
|
||||||
|
}
|
||||||
|
|
||||||
|
GHContentUpdateResponse response = requester.to(getApiRoute(), GHContentUpdateResponse.class);
|
||||||
|
|
||||||
|
response.getContent().wrap(owner);
|
||||||
|
response.getCommit().wrapUp(owner);
|
||||||
|
|
||||||
|
this.content = encodedContent;
|
||||||
|
return response;
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHContentUpdateResponse delete(String message) throws IOException {
|
||||||
|
return delete(message, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHContentUpdateResponse delete(String commitMessage, String branch) throws IOException {
|
||||||
|
Requester requester = new Requester(owner.root)
|
||||||
|
.with("path", path)
|
||||||
|
.with("message", commitMessage)
|
||||||
|
.with("sha", sha)
|
||||||
|
.method("DELETE");
|
||||||
|
|
||||||
|
if (branch != null) {
|
||||||
|
requester.with("branch", branch);
|
||||||
|
}
|
||||||
|
|
||||||
|
GHContentUpdateResponse response = requester.to(getApiRoute(), GHContentUpdateResponse.class);
|
||||||
|
|
||||||
|
response.getCommit().wrapUp(owner);
|
||||||
|
return response;
|
||||||
|
}
|
||||||
|
|
||||||
|
private String getApiRoute() {
|
||||||
|
return "/repos/" + owner.getOwnerName() + "/" + owner.getName() + "/contents/" + path;
|
||||||
|
}
|
||||||
|
|
||||||
|
GHContent wrap(GHRepository owner) {
|
||||||
|
this.owner = owner;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static GHContent[] wrap(GHContent[] contents, GHRepository repository) {
|
||||||
|
for (GHContent unwrappedContent : contents) {
|
||||||
|
unwrappedContent.wrap(repository);
|
||||||
|
}
|
||||||
|
return contents;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,18 @@
|
|||||||
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The response that is returned when updating
|
||||||
|
* repository content.
|
||||||
|
**/
|
||||||
|
public final class GHContentUpdateResponse {
|
||||||
|
private GHContent content;
|
||||||
|
private GHCommit commit;
|
||||||
|
|
||||||
|
public GHContent getContent() {
|
||||||
|
return content;
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHCommit getCommit() {
|
||||||
|
return commit;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -6,6 +6,7 @@ package org.kohsuke.github;
|
|||||||
* See http://developer.github.com/v3/events/types/
|
* See http://developer.github.com/v3/events/types/
|
||||||
*
|
*
|
||||||
* @author Kohsuke Kawaguchi
|
* @author Kohsuke Kawaguchi
|
||||||
|
* @see GHEventInfo
|
||||||
*/
|
*/
|
||||||
public enum GHEvent {
|
public enum GHEvent {
|
||||||
COMMIT_COMMENT,
|
COMMIT_COMMENT,
|
||||||
@@ -22,6 +23,7 @@ public enum GHEvent {
|
|||||||
MEMBER,
|
MEMBER,
|
||||||
PUBLIC,
|
PUBLIC,
|
||||||
PULL_REQUEST,
|
PULL_REQUEST,
|
||||||
|
PULL_REQUEST_REVIEW_COMMENT,
|
||||||
PUSH,
|
PUSH,
|
||||||
TEAM_ADD,
|
TEAM_ADD,
|
||||||
WATCH
|
WATCH
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
package org.kohsuke.github;
|
package org.kohsuke.github;
|
||||||
|
|
||||||
import org.codehaus.jackson.node.ObjectNode;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.databind.node.ObjectNode;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Represents an event.
|
* Represents an event.
|
||||||
*
|
*
|
||||||
@@ -63,6 +63,13 @@ public class GHEventInfo {
|
|||||||
return root.getUser(actor.getLogin());
|
return root.getUser(actor.getLogin());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Quick way to just get the actor of the login.
|
||||||
|
*/
|
||||||
|
public String getActorLogin() throws IOException {
|
||||||
|
return actor.getLogin();
|
||||||
|
}
|
||||||
|
|
||||||
public GHOrganization getOrganization() throws IOException {
|
public GHOrganization getOrganization() throws IOException {
|
||||||
return (org==null || org.getLogin()==null) ? null : root.getOrganization(org.getLogin());
|
return (org==null || org.getLogin()==null) ? null : root.getOrganization(org.getLogin());
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package org.kohsuke.github;
|
package org.kohsuke.github;
|
||||||
|
|
||||||
import java.io.Reader;
|
import java.io.Reader;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Base type for types used in databinding of the event payload.
|
* Base type for types used in databinding of the event payload.
|
||||||
@@ -8,6 +9,7 @@ import java.io.Reader;
|
|||||||
* @see GitHub#parseEventPayload(Reader, Class)
|
* @see GitHub#parseEventPayload(Reader, Class)
|
||||||
* @see GHEventInfo#getPayload(Class)
|
* @see GHEventInfo#getPayload(Class)
|
||||||
*/
|
*/
|
||||||
|
@SuppressWarnings("UnusedDeclaration")
|
||||||
public abstract class GHEventPayload {
|
public abstract class GHEventPayload {
|
||||||
protected GitHub root;
|
protected GitHub root;
|
||||||
|
|
||||||
@@ -21,7 +23,7 @@ public abstract class GHEventPayload {
|
|||||||
/**
|
/**
|
||||||
* A pull request status has changed.
|
* A pull request status has changed.
|
||||||
*
|
*
|
||||||
* @see http://developer.github.com/v3/activity/events/types/#pullrequestevent
|
* @see <a href="http://developer.github.com/v3/activity/events/types/#pullrequestevent">authoritative source</a>
|
||||||
*/
|
*/
|
||||||
public static class PullRequest extends GHEventPayload {
|
public static class PullRequest extends GHEventPayload {
|
||||||
private String action;
|
private String action;
|
||||||
@@ -61,7 +63,7 @@ public abstract class GHEventPayload {
|
|||||||
/**
|
/**
|
||||||
* A comment was added to an issue
|
* A comment was added to an issue
|
||||||
*
|
*
|
||||||
* @see http://developer.github.com/v3/activity/events/types/#issuecommentevent
|
* @see <a href="http://developer.github.com/v3/activity/events/types/#issuecommentevent">authoritative source</a>
|
||||||
*/
|
*/
|
||||||
public static class IssueComment extends GHEventPayload {
|
public static class IssueComment extends GHEventPayload {
|
||||||
private String action;
|
private String action;
|
||||||
@@ -105,4 +107,88 @@ public abstract class GHEventPayload {
|
|||||||
comment.wrapUp(issue);
|
comment.wrapUp(issue);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A commit was pushed.
|
||||||
|
*
|
||||||
|
* @see <a href="http://developer.github.com/v3/activity/events/types/#pushevent">authoritative source</a>
|
||||||
|
*/
|
||||||
|
public static class Push extends GHEventPayload {
|
||||||
|
private String head, before;
|
||||||
|
private String ref;
|
||||||
|
private int size;
|
||||||
|
private List<PushCommit> commits;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The SHA of the HEAD commit on the repository
|
||||||
|
*/
|
||||||
|
public String getHead() {
|
||||||
|
return head;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This is undocumented, but it looks like this captures the commit that the ref was pointing to
|
||||||
|
* before the push.
|
||||||
|
*/
|
||||||
|
public String getBefore() {
|
||||||
|
return before;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The full Git ref that was pushed. Example: “refs/heads/master”
|
||||||
|
*/
|
||||||
|
public String getRef() {
|
||||||
|
return ref;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The number of commits in the push.
|
||||||
|
* Is this always the same as {@code getCommits().size()}?
|
||||||
|
*/
|
||||||
|
public int getSize() {
|
||||||
|
return size;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The list of pushed commits.
|
||||||
|
*/
|
||||||
|
public List<PushCommit> getCommits() {
|
||||||
|
return commits;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Commit in a push
|
||||||
|
*/
|
||||||
|
public static class PushCommit {
|
||||||
|
private GitUser author;
|
||||||
|
private String url, sha, message;
|
||||||
|
private boolean distinct;
|
||||||
|
|
||||||
|
public GitUser getAuthor() {
|
||||||
|
return author;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Points to the commit API resource.
|
||||||
|
*/
|
||||||
|
public String getUrl() {
|
||||||
|
return url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getSha() {
|
||||||
|
return sha;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getMessage() {
|
||||||
|
return message;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Whether this commit is distinct from any that have been pushed before.
|
||||||
|
*/
|
||||||
|
public boolean isDistinct() {
|
||||||
|
return distinct;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -49,7 +49,7 @@ public class GHIssue {
|
|||||||
protected String closed_at;
|
protected String closed_at;
|
||||||
protected int comments;
|
protected int comments;
|
||||||
protected String body;
|
protected String body;
|
||||||
protected List<String> labels;
|
protected List<Label> labels;
|
||||||
protected GHUser user;
|
protected GHUser user;
|
||||||
protected String title, created_at, html_url;
|
protected String title, created_at, html_url;
|
||||||
protected GHIssue.PullRequest pull_request;
|
protected GHIssue.PullRequest pull_request;
|
||||||
@@ -58,6 +58,24 @@ public class GHIssue {
|
|||||||
protected int id;
|
protected int id;
|
||||||
protected GHUser closed_by;
|
protected GHUser closed_by;
|
||||||
|
|
||||||
|
public static class Label {
|
||||||
|
private String url;
|
||||||
|
private String name;
|
||||||
|
private String color;
|
||||||
|
|
||||||
|
public String getUrl() {
|
||||||
|
return url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getColor() {
|
||||||
|
return color;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/*package*/ GHIssue wrap(GHRepository owner) {
|
/*package*/ GHIssue wrap(GHRepository owner) {
|
||||||
this.owner = owner;
|
this.owner = owner;
|
||||||
this.root = owner.root;
|
this.root = owner.root;
|
||||||
@@ -111,7 +129,7 @@ public class GHIssue {
|
|||||||
return Enum.valueOf(GHIssueState.class, state.toUpperCase(Locale.ENGLISH));
|
return Enum.valueOf(GHIssueState.class, state.toUpperCase(Locale.ENGLISH));
|
||||||
}
|
}
|
||||||
|
|
||||||
public Collection<String> getLabels() {
|
public Collection<Label> getLabels() {
|
||||||
if(labels == null){
|
if(labels == null){
|
||||||
return Collections.EMPTY_LIST;
|
return Collections.EMPTY_LIST;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,9 +10,9 @@ import org.apache.commons.lang.builder.ToStringBuilder;
|
|||||||
public class GHKey {
|
public class GHKey {
|
||||||
/*package almost final*/ GitHub root;
|
/*package almost final*/ GitHub root;
|
||||||
|
|
||||||
private String url, key, title;
|
protected String url, key, title;
|
||||||
private boolean verified;
|
protected boolean verified;
|
||||||
private int id;
|
protected int id;
|
||||||
|
|
||||||
public int getId() {
|
public int getId() {
|
||||||
return id;
|
return id;
|
||||||
|
|||||||
@@ -3,7 +3,12 @@ package org.kohsuke.github;
|
|||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Iterator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
|
import java.util.TreeMap;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Represents the account that's logging into GitHub.
|
* Represents the account that's logging into GitHub.
|
||||||
@@ -29,13 +34,74 @@ public class GHMyself extends GHUser {
|
|||||||
/**
|
/**
|
||||||
* Returns the read-only list of all the pulic keys of the current user.
|
* Returns the read-only list of all the pulic keys of the current user.
|
||||||
*
|
*
|
||||||
|
* NOTE: When using OAuth authenticaiton, the READ/WRITE User scope is
|
||||||
|
* required by the GitHub APIs, otherwise you will get a 404 NOT FOUND.
|
||||||
|
*
|
||||||
* @return
|
* @return
|
||||||
* Always non-null.
|
* Always non-null.
|
||||||
*/
|
*/
|
||||||
public List<GHKey> getPublicKeys() throws IOException {
|
public List<GHKey> getPublicKeys() throws IOException {
|
||||||
return Collections.unmodifiableList(Arrays.asList(root.retrieve().to("/user/keys", GHKey[].class)));
|
return Collections.unmodifiableList(Arrays.asList(root.retrieve().to("/user/keys", GHKey[].class)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the read-only list of all the pulic verified keys of the current user.
|
||||||
|
*
|
||||||
|
* Differently from the getPublicKeys() method, the retrieval of the user's
|
||||||
|
* verified public keys does not require any READ/WRITE OAuth Scope to the
|
||||||
|
* user's profile.
|
||||||
|
*
|
||||||
|
* @return
|
||||||
|
* Always non-null.
|
||||||
|
*/
|
||||||
|
public List<GHVerifiedKey> getPublicVerifiedKeys() throws IOException {
|
||||||
|
return Collections.unmodifiableList(Arrays.asList(root.retrieve().to(
|
||||||
|
"/users/" + getLogin() + "/keys", GHVerifiedKey[].class)));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the organization that this user belongs to.
|
||||||
|
*/
|
||||||
|
public GHPersonSet<GHOrganization> getAllOrganizations() throws IOException {
|
||||||
|
GHPersonSet<GHOrganization> orgs = new GHPersonSet<GHOrganization>();
|
||||||
|
Set<String> names = new HashSet<String>();
|
||||||
|
for (GHOrganization o : root.retrieve().to("/user/orgs", GHOrganization[].class)) {
|
||||||
|
if (names.add(o.getLogin())) // in case of rumoured duplicates in the data
|
||||||
|
orgs.add(root.getOrganization(o.getLogin()));
|
||||||
|
}
|
||||||
|
return orgs;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the all repositories this user owns (public and private).
|
||||||
|
*/
|
||||||
|
public synchronized Map<String,GHRepository> getAllRepositories() throws IOException {
|
||||||
|
Map<String,GHRepository> repositories = new TreeMap<String, GHRepository>();
|
||||||
|
for (GHRepository r : listAllRepositories()) {
|
||||||
|
repositories.put(r.getName(),r);
|
||||||
|
}
|
||||||
|
return Collections.unmodifiableMap(repositories);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Lists up all repositories this user owns (public and private).
|
||||||
|
*
|
||||||
|
* Unlike {@link #getAllRepositories()}, this does not wait until all the repositories are returned.
|
||||||
|
*/
|
||||||
|
public PagedIterable<GHRepository> listAllRepositories() {
|
||||||
|
return new PagedIterable<GHRepository>() {
|
||||||
|
public PagedIterator<GHRepository> iterator() {
|
||||||
|
return new PagedIterator<GHRepository>(root.retrieve().asIterator("/user/repos", GHRepository[].class)) {
|
||||||
|
@Override
|
||||||
|
protected void wrapUp(GHRepository[] page) {
|
||||||
|
for (GHRepository c : page)
|
||||||
|
c.wrap(root);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
// public void addEmails(Collection<String> emails) throws IOException {
|
// public void addEmails(Collection<String> emails) throws IOException {
|
||||||
//// new Requester(root,ApiVersion.V3).withCredential().to("/user/emails");
|
//// new Requester(root,ApiVersion.V3).withCredential().to("/user/emails");
|
||||||
// root.retrieveWithAuth3()
|
// root.retrieveWithAuth3()
|
||||||
|
|||||||
@@ -156,4 +156,21 @@ public class GHOrganization extends GHPerson {
|
|||||||
}
|
}
|
||||||
return all;
|
return all;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Lists events performed by a user (this includes private events if the caller is authenticated.
|
||||||
|
*/
|
||||||
|
public PagedIterable<GHEventInfo> listEvents() throws IOException {
|
||||||
|
return new PagedIterable<GHEventInfo>() {
|
||||||
|
public PagedIterator<GHEventInfo> iterator() {
|
||||||
|
return new PagedIterator<GHEventInfo>(root.retrieve().asIterator(String.format("/orgs/%s/events", login), GHEventInfo[].class)) {
|
||||||
|
@Override
|
||||||
|
protected void wrapUp(GHEventInfo[] page) {
|
||||||
|
for (GHEventInfo c : page)
|
||||||
|
c.wrapUp(root);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -55,14 +55,25 @@ public abstract class GHPerson {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Lists up all the repositories.
|
* Lists up all the repositories using a 30 items page size.
|
||||||
*
|
*
|
||||||
* Unlike {@link #getRepositories()}, this does not wait until all the repositories are returned.
|
* Unlike {@link #getRepositories()}, this does not wait until all the repositories are returned.
|
||||||
*/
|
*/
|
||||||
public PagedIterable<GHRepository> listRepositories() {
|
public PagedIterable<GHRepository> listRepositories() {
|
||||||
|
return listRepositories(30);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Lists up all the repositories using the specified page size.
|
||||||
|
*
|
||||||
|
* @param pageSize size for each page of items returned by GitHub. Maximum page size is 100.
|
||||||
|
*
|
||||||
|
* Unlike {@link #getRepositories()}, this does not wait until all the repositories are returned.
|
||||||
|
*/
|
||||||
|
public PagedIterable<GHRepository> listRepositories(final int pageSize) {
|
||||||
return new PagedIterable<GHRepository>() {
|
return new PagedIterable<GHRepository>() {
|
||||||
public PagedIterator<GHRepository> iterator() {
|
public PagedIterator<GHRepository> iterator() {
|
||||||
return new PagedIterator<GHRepository>(root.retrieve().asIterator("/users/" + login + "/repos", GHRepository[].class)) {
|
return new PagedIterator<GHRepository>(root.retrieve().asIterator("/users/" + login + "/repos?per_page=" + pageSize, GHRepository[].class)) {
|
||||||
@Override
|
@Override
|
||||||
protected void wrapUp(GHRepository[] page) {
|
protected void wrapUp(GHRepository[] page) {
|
||||||
for (GHRepository c : page)
|
for (GHRepository c : page)
|
||||||
@@ -124,6 +135,11 @@ public abstract class GHPerson {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Lists events for an organization or an user.
|
||||||
|
*/
|
||||||
|
public abstract PagedIterable<GHEventInfo> listEvents() throws IOException;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gravatar ID of this user, like 0cb9832a01c22c083390f3c5dcb64105
|
* Gravatar ID of this user, like 0cb9832a01c22c083390f3c5dcb64105
|
||||||
*
|
*
|
||||||
@@ -224,5 +240,4 @@ public abstract class GHPerson {
|
|||||||
populate();
|
populate();
|
||||||
return followers;
|
return followers;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -27,6 +27,7 @@ import java.io.IOException;
|
|||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
|
import java.util.Locale;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A pull request.
|
* A pull request.
|
||||||
@@ -118,7 +119,7 @@ public class GHPullRequest extends GHIssue {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Collection<String> getLabels() {
|
public Collection<Label> getLabels() {
|
||||||
return super.getLabels();
|
return super.getLabels();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -186,4 +187,22 @@ public class GHPullRequest extends GHIssue {
|
|||||||
|
|
||||||
root.retrieve().to(url, this);
|
root.retrieve().to(url, this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retrieves all the commits associated to this pull request.
|
||||||
|
*/
|
||||||
|
public PagedIterable<GHPullRequestCommitDetail> listCommits() {
|
||||||
|
return new PagedIterable<GHPullRequestCommitDetail>() {
|
||||||
|
public PagedIterator<GHPullRequestCommitDetail> iterator() {
|
||||||
|
return new PagedIterator<GHPullRequestCommitDetail>(root.retrieve().asIterator(
|
||||||
|
String.format("%s/commits", getApiURL().getPath()),
|
||||||
|
GHPullRequestCommitDetail[].class)) {
|
||||||
|
@Override
|
||||||
|
protected void wrapUp(GHPullRequestCommitDetail[] page) {
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
129
src/main/java/org/kohsuke/github/GHPullRequestCommitDetail.java
Normal file
129
src/main/java/org/kohsuke/github/GHPullRequestCommitDetail.java
Normal file
@@ -0,0 +1,129 @@
|
|||||||
|
/*
|
||||||
|
* The MIT License
|
||||||
|
*
|
||||||
|
* Copyright (c) 2013, Luca Milanesio
|
||||||
|
*
|
||||||
|
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
* of this software and associated documentation files (the "Software"), to deal
|
||||||
|
* in the Software without restriction, including without limitation the rights
|
||||||
|
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
* copies of the Software, and to permit persons to whom the Software is
|
||||||
|
* furnished to do so, subject to the following conditions:
|
||||||
|
*
|
||||||
|
* The above copyright notice and this permission notice shall be included in
|
||||||
|
* all copies or substantial portions of the Software.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
* SOFTWARE.
|
||||||
|
*/
|
||||||
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
import com.infradna.tool.bridge_method_injector.WithBridgeMethods;
|
||||||
|
|
||||||
|
import java.net.URL;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Commit detail inside a {@link GHPullRequest}.
|
||||||
|
*
|
||||||
|
* @author Luca Milanesio
|
||||||
|
*/
|
||||||
|
public class GHPullRequestCommitDetail {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @deprecated Use {@link GitUser}
|
||||||
|
*/
|
||||||
|
public static class Authorship extends GitUser {}
|
||||||
|
|
||||||
|
public static class Tree {
|
||||||
|
String sha;
|
||||||
|
String url;
|
||||||
|
|
||||||
|
public String getSha() {
|
||||||
|
return sha;
|
||||||
|
}
|
||||||
|
|
||||||
|
public URL getUrl() {
|
||||||
|
return GitHub.parseURL(url);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class Commit {
|
||||||
|
Authorship author;
|
||||||
|
Authorship committer;
|
||||||
|
String message;
|
||||||
|
Tree tree;
|
||||||
|
String url;
|
||||||
|
int comment_count;
|
||||||
|
|
||||||
|
@WithBridgeMethods(value=Authorship.class,castRequired=true)
|
||||||
|
public GitUser getAuthor() {
|
||||||
|
return author;
|
||||||
|
}
|
||||||
|
|
||||||
|
@WithBridgeMethods(value=Authorship.class,castRequired=true)
|
||||||
|
public GitUser getCommitter() {
|
||||||
|
return committer;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getMessage() {
|
||||||
|
return message;
|
||||||
|
}
|
||||||
|
|
||||||
|
public URL getUrl() {
|
||||||
|
return GitHub.parseURL(url);
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getComment_count() {
|
||||||
|
return comment_count;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class CommitPointer {
|
||||||
|
String sha;
|
||||||
|
String url;
|
||||||
|
String html_url;
|
||||||
|
|
||||||
|
public URL getUrl() {
|
||||||
|
return GitHub.parseURL(url);
|
||||||
|
}
|
||||||
|
|
||||||
|
public URL getHtml_url() {
|
||||||
|
return GitHub.parseURL(html_url);
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getSha() {
|
||||||
|
return sha;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
String sha;
|
||||||
|
Commit commit;
|
||||||
|
String url;
|
||||||
|
String html_url;
|
||||||
|
String comments_url;
|
||||||
|
CommitPointer[] parents;
|
||||||
|
|
||||||
|
public String getSha() {
|
||||||
|
return sha;
|
||||||
|
}
|
||||||
|
public Commit getCommit() {
|
||||||
|
return commit;
|
||||||
|
}
|
||||||
|
public URL getApiUrl() {
|
||||||
|
return GitHub.parseURL(url);
|
||||||
|
}
|
||||||
|
public URL getUrl() {
|
||||||
|
return GitHub.parseURL(html_url);
|
||||||
|
}
|
||||||
|
public URL getCommentsUrl() {
|
||||||
|
return GitHub.parseURL(comments_url);
|
||||||
|
}
|
||||||
|
public CommitPointer[] getParents() {
|
||||||
|
return parents;
|
||||||
|
}
|
||||||
|
}
|
||||||
195
src/main/java/org/kohsuke/github/GHRelease.java
Normal file
195
src/main/java/org/kohsuke/github/GHRelease.java
Normal file
@@ -0,0 +1,195 @@
|
|||||||
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.FileInputStream;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.Date;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
import static java.lang.String.format;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Release in a github repository.
|
||||||
|
*
|
||||||
|
* @see GHRepository#getReleases()
|
||||||
|
* @see GHRepository#createRelease(String)
|
||||||
|
*/
|
||||||
|
public class GHRelease {
|
||||||
|
GitHub root;
|
||||||
|
GHRepository owner;
|
||||||
|
|
||||||
|
private String url;
|
||||||
|
private String html_url;
|
||||||
|
private String assets_url;
|
||||||
|
private String upload_url;
|
||||||
|
private long id;
|
||||||
|
private String tag_name;
|
||||||
|
private String target_commitish;
|
||||||
|
private String name;
|
||||||
|
private String body;
|
||||||
|
private boolean draft;
|
||||||
|
private boolean prerelease;
|
||||||
|
private Date created_at;
|
||||||
|
private Date published_at;
|
||||||
|
|
||||||
|
public String getAssetsUrl() {
|
||||||
|
return assets_url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setAssetsUrl(String assets_url) {
|
||||||
|
this.assets_url = assets_url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getBody() {
|
||||||
|
return body;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setBody(String body) {
|
||||||
|
this.body = body;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Date getCreatedAt() {
|
||||||
|
return created_at;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setCreatedAt(Date created_at) {
|
||||||
|
this.created_at = created_at;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isDraft() {
|
||||||
|
return draft;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setDraft(boolean draft) {
|
||||||
|
this.draft = draft;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getHtmlUrl() {
|
||||||
|
return html_url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setHtmlUrl(String html_url) {
|
||||||
|
this.html_url = html_url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public long getId() {
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setId(long id) {
|
||||||
|
this.id = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setName(String name) {
|
||||||
|
this.name = name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHRepository getOwner() {
|
||||||
|
return owner;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setOwner(GHRepository owner) {
|
||||||
|
this.owner = owner;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isPrerelease() {
|
||||||
|
return prerelease;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setPrerelease(boolean prerelease) {
|
||||||
|
this.prerelease = prerelease;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Date getPublished_at() {
|
||||||
|
return published_at;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setPublished_at(Date published_at) {
|
||||||
|
this.published_at = published_at;
|
||||||
|
}
|
||||||
|
|
||||||
|
public GitHub getRoot() {
|
||||||
|
return root;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRoot(GitHub root) {
|
||||||
|
this.root = root;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getTagName() {
|
||||||
|
return tag_name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTagName(String tag_name) {
|
||||||
|
this.tag_name = tag_name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getTargetCommitish() {
|
||||||
|
return target_commitish;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTargetCommitish(String target_commitish) {
|
||||||
|
this.target_commitish = target_commitish;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getUploadUrl() {
|
||||||
|
return upload_url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUploadUrl(String upload_url) {
|
||||||
|
this.upload_url = upload_url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getUrl() {
|
||||||
|
return url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUrl(String url) {
|
||||||
|
this.url = url;
|
||||||
|
}
|
||||||
|
|
||||||
|
GHRelease wrap(GHRepository owner) {
|
||||||
|
this.owner = owner;
|
||||||
|
this.root = owner.root;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
static GHRelease[] wrap(GHRelease[] releases, GHRepository owner) {
|
||||||
|
for (GHRelease release : releases) {
|
||||||
|
release.wrap(owner);
|
||||||
|
}
|
||||||
|
return releases;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Because github relies on SNI (http://en.wikipedia.org/wiki/Server_Name_Indication) this method will only work on
|
||||||
|
* Java 7 or greater. Options for fixing this for earlier JVMs can be found here
|
||||||
|
* http://stackoverflow.com/questions/12361090/server-name-indication-sni-on-java but involve more complicated
|
||||||
|
* handling of the HTTP requests to github's API.
|
||||||
|
*
|
||||||
|
* @throws IOException
|
||||||
|
*/
|
||||||
|
public GHAsset uploadAsset(File file, String contentType) throws IOException {
|
||||||
|
Requester builder = new Requester(owner.root);
|
||||||
|
|
||||||
|
String url = format("https://uploads.github.com%sreleases/%d/assets?name=%s",
|
||||||
|
owner.getApiTailUrl(""), getId(), file.getName());
|
||||||
|
return builder.contentType(contentType)
|
||||||
|
.with(new FileInputStream(file))
|
||||||
|
.to(url, GHAsset.class).wrap(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<GHAsset> getAssets() throws IOException {
|
||||||
|
Requester builder = new Requester(owner.root);
|
||||||
|
|
||||||
|
GHAsset[] assets = builder
|
||||||
|
.method("GET")
|
||||||
|
.to(owner.getApiTailUrl(format("releases/%d/assets", id)), GHAsset[].class);
|
||||||
|
return Arrays.asList(GHAsset.wrap(assets, this));
|
||||||
|
}
|
||||||
|
}
|
||||||
80
src/main/java/org/kohsuke/github/GHReleaseBuilder.java
Normal file
80
src/main/java/org/kohsuke/github/GHReleaseBuilder.java
Normal file
@@ -0,0 +1,80 @@
|
|||||||
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Builder pattern for creating a {@link GHRelease}
|
||||||
|
*
|
||||||
|
* @see GHRepository#createRelease(String)
|
||||||
|
*/
|
||||||
|
public class GHReleaseBuilder {
|
||||||
|
private final GHRepository repo;
|
||||||
|
private final Requester builder;
|
||||||
|
|
||||||
|
public GHReleaseBuilder(GHRepository ghRepository, String tag) {
|
||||||
|
this.repo = ghRepository;
|
||||||
|
this.builder = new Requester(repo.root);
|
||||||
|
builder.with("tag_name", tag);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param body The release notes body.
|
||||||
|
*/
|
||||||
|
public GHReleaseBuilder body(String body) {
|
||||||
|
if (body != null) {
|
||||||
|
builder.with("body", body);
|
||||||
|
}
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Specifies the commitish value that determines where the Git tag is created from. Can be any branch or
|
||||||
|
* commit SHA.
|
||||||
|
*
|
||||||
|
* @param commitish Defaults to the repository’s default branch (usually "master"). Unused if the Git tag
|
||||||
|
* already exists.
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public GHReleaseBuilder commitish(String commitish) {
|
||||||
|
if (commitish != null) {
|
||||||
|
builder.with("target_commitish", commitish);
|
||||||
|
}
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Optional.
|
||||||
|
*
|
||||||
|
* @param draft {@code true} to create a draft (unpublished) release, {@code false} to create a published one.
|
||||||
|
* Default is {@code false}.
|
||||||
|
*/
|
||||||
|
public GHReleaseBuilder draft(boolean draft) {
|
||||||
|
builder.with("draft", draft);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param name the name of the release
|
||||||
|
*/
|
||||||
|
public GHReleaseBuilder name(String name) {
|
||||||
|
if (name != null) {
|
||||||
|
builder.with("name", name);
|
||||||
|
}
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Optional
|
||||||
|
*
|
||||||
|
* @param prerelease {@code true} to identify the release as a prerelease. {@code false} to identify the release
|
||||||
|
* as a full release. Default is {@code false}.
|
||||||
|
*/
|
||||||
|
public GHReleaseBuilder prerelease(boolean prerelease) {
|
||||||
|
builder.with("prerelease", prerelease);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHRelease create() throws IOException {
|
||||||
|
return builder.to(repo.getApiTailUrl("releases"), GHRelease.class).wrap(repo);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -42,6 +42,7 @@ import java.util.Locale;
|
|||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.TreeMap;
|
import java.util.TreeMap;
|
||||||
|
import javax.xml.bind.DatatypeConverter;
|
||||||
|
|
||||||
import static java.util.Arrays.*;
|
import static java.util.Arrays.*;
|
||||||
|
|
||||||
@@ -143,7 +144,33 @@ public class GHRepository {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public List<GHIssue> getIssues(GHIssueState state) throws IOException {
|
public List<GHIssue> getIssues(GHIssueState state) throws IOException {
|
||||||
return Arrays.asList(GHIssue.wrap(root.retrieve().to("/repos/" + owner.login + "/" + name + "/issues?state=" + state.toString().toLowerCase(), GHIssue[].class), this));
|
return listIssues(state).asList();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Lists up all the issues in this repository.
|
||||||
|
*/
|
||||||
|
public PagedIterable<GHIssue> listIssues(final GHIssueState state) {
|
||||||
|
return new PagedIterable<GHIssue>() {
|
||||||
|
public PagedIterator<GHIssue> iterator() {
|
||||||
|
return new PagedIterator<GHIssue>(root.retrieve().asIterator(getApiTailUrl("issues?state="+state.toString().toLowerCase(Locale.ENGLISH)), GHIssue[].class)) {
|
||||||
|
@Override
|
||||||
|
protected void wrapUp(GHIssue[] page) {
|
||||||
|
for (GHIssue c : page)
|
||||||
|
c.wrap(GHRepository.this);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHReleaseBuilder createRelease(String tag) {
|
||||||
|
return new GHReleaseBuilder(this,tag);
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<GHRelease> getReleases() throws IOException {
|
||||||
|
return Arrays.asList(GHRelease.wrap(root.retrieve().to("/repos/" + owner.login + "/" + name + "/releases",
|
||||||
|
GHRelease[].class), this));
|
||||||
}
|
}
|
||||||
|
|
||||||
protected String getOwnerName() {
|
protected String getOwnerName() {
|
||||||
@@ -519,6 +546,22 @@ public class GHRepository {
|
|||||||
.to(String.format("/repos/%s/%s/statuses/%s",owner.login,this.name,sha1),GHCommitStatus.class).wrapUp(root);
|
.to(String.format("/repos/%s/%s/statuses/%s",owner.login,this.name,sha1),GHCommitStatus.class).wrapUp(root);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Lists repository events.
|
||||||
|
*/
|
||||||
|
public PagedIterable<GHEventInfo> listEvents() throws IOException {
|
||||||
|
return new PagedIterable<GHEventInfo>() {
|
||||||
|
public PagedIterator<GHEventInfo> iterator() {
|
||||||
|
return new PagedIterator<GHEventInfo>(root.retrieve().asIterator(String.format("/repos/%s/%s/events", owner.login, name), GHEventInfo[].class)) {
|
||||||
|
@Override
|
||||||
|
protected void wrapUp(GHEventInfo[] page) {
|
||||||
|
for (GHEventInfo c : page)
|
||||||
|
c.wrapUp(root);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
@@ -691,7 +734,66 @@ public class GHRepository {
|
|||||||
}
|
}
|
||||||
return m;
|
return m;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public GHContent getFileContent(String path) throws IOException {
|
||||||
|
return getFileContent(path, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHContent getFileContent(String path, String ref) throws IOException {
|
||||||
|
Requester requester = root.retrieve();
|
||||||
|
String target = String.format("/repos/%s/%s/contents/%s", owner.login, name, path);
|
||||||
|
|
||||||
|
if (ref != null)
|
||||||
|
target = target + "?ref=" + ref;
|
||||||
|
|
||||||
|
return requester.to(target, GHContent.class).wrap(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<GHContent> getDirectoryContent(String path) throws IOException {
|
||||||
|
return getDirectoryContent(path, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<GHContent> getDirectoryContent(String path, String ref) throws IOException {
|
||||||
|
Requester requester = root.retrieve();
|
||||||
|
String target = String.format("/repos/%s/%s/contents/%s", owner.login, name, path);
|
||||||
|
|
||||||
|
if (ref != null)
|
||||||
|
target = target + "?ref=" + ref;
|
||||||
|
|
||||||
|
GHContent[] files = requester.to(target, GHContent[].class);
|
||||||
|
|
||||||
|
GHContent.wrap(files, this);
|
||||||
|
|
||||||
|
return Arrays.asList(files);
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHContent getReadme() throws Exception {
|
||||||
|
return getFileContent("readme");
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHContentUpdateResponse createContent(String content, String commitMessage, String path) throws IOException {
|
||||||
|
return createContent(content, commitMessage, path, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
public GHContentUpdateResponse createContent(String content, String commitMessage, String path, String branch) throws IOException {
|
||||||
|
Requester requester = new Requester(root)
|
||||||
|
.with("path", path)
|
||||||
|
.with("message", commitMessage)
|
||||||
|
.with("content", DatatypeConverter.printBase64Binary(content.getBytes()))
|
||||||
|
.method("PUT");
|
||||||
|
|
||||||
|
if (branch != null) {
|
||||||
|
requester.with("branch", branch);
|
||||||
|
}
|
||||||
|
|
||||||
|
GHContentUpdateResponse response = requester.to(getApiTailUrl("contents/" + path), GHContentUpdateResponse.class);
|
||||||
|
|
||||||
|
response.getContent().wrap(this);
|
||||||
|
response.getCommit().wrapUp(this);
|
||||||
|
|
||||||
|
return response;
|
||||||
|
}
|
||||||
|
|
||||||
public GHMilestone createMilestone(String title, String description) throws IOException {
|
public GHMilestone createMilestone(String title, String description) throws IOException {
|
||||||
return new Requester(root)
|
return new Requester(root)
|
||||||
.with("title", title).with("description", description).method("POST").to(getApiTailUrl("milestones"), GHMilestone.class).wrap(this);
|
.with("title", title).with("description", description).method("POST").to(getApiTailUrl("milestones"), GHMilestone.class).wrap(this);
|
||||||
|
|||||||
@@ -103,6 +103,23 @@ public class GHUser extends GHPerson {
|
|||||||
return orgs;
|
return orgs;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Lists events performed by a user (this includes private events if the caller is authenticated.
|
||||||
|
*/
|
||||||
|
public PagedIterable<GHEventInfo> listEvents() throws IOException {
|
||||||
|
return new PagedIterable<GHEventInfo>() {
|
||||||
|
public PagedIterator<GHEventInfo> iterator() {
|
||||||
|
return new PagedIterator<GHEventInfo>(root.retrieve().asIterator(String.format("/users/%s/events", login), GHEventInfo[].class)) {
|
||||||
|
@Override
|
||||||
|
protected void wrapUp(GHEventInfo[] page) {
|
||||||
|
for (GHEventInfo c : page)
|
||||||
|
c.wrapUp(root);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return "User:"+login;
|
return "User:"+login;
|
||||||
|
|||||||
13
src/main/java/org/kohsuke/github/GHVerifiedKey.java
Normal file
13
src/main/java/org/kohsuke/github/GHVerifiedKey.java
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
public class GHVerifiedKey extends GHKey {
|
||||||
|
|
||||||
|
public GHVerifiedKey() {
|
||||||
|
this.verified = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getTitle() {
|
||||||
|
return (title == null ? "key-" + id : title);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -23,12 +23,7 @@
|
|||||||
*/
|
*/
|
||||||
package org.kohsuke.github;
|
package org.kohsuke.github;
|
||||||
|
|
||||||
import com.infradna.tool.bridge_method_injector.WithBridgeMethods;
|
import static com.fasterxml.jackson.annotation.JsonAutoDetect.Visibility.*;
|
||||||
import org.apache.commons.codec.binary.Base64;
|
|
||||||
import org.apache.commons.io.IOUtils;
|
|
||||||
import org.codehaus.jackson.map.DeserializationConfig.Feature;
|
|
||||||
import org.codehaus.jackson.map.ObjectMapper;
|
|
||||||
import org.codehaus.jackson.map.introspect.VisibilityChecker.Std;
|
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileInputStream;
|
import java.io.FileInputStream;
|
||||||
@@ -47,7 +42,13 @@ import java.util.Map;
|
|||||||
import java.util.Properties;
|
import java.util.Properties;
|
||||||
import java.util.TimeZone;
|
import java.util.TimeZone;
|
||||||
|
|
||||||
import static org.codehaus.jackson.annotate.JsonAutoDetect.Visibility.*;
|
import org.apache.commons.codec.binary.Base64;
|
||||||
|
import org.apache.commons.io.IOUtils;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||||
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
import com.fasterxml.jackson.databind.introspect.VisibilityChecker.Std;
|
||||||
|
import com.infradna.tool.bridge_method_injector.WithBridgeMethods;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Root of the GitHub API.
|
* Root of the GitHub API.
|
||||||
@@ -192,8 +193,16 @@ public class GitHub {
|
|||||||
return new GitHub(null,null,null);
|
return new GitHub(null,null,null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Is this an anonymous connection
|
||||||
|
* @return {@code true} if operations that require authentication will fail.
|
||||||
|
*/
|
||||||
|
public boolean isAnonymous() {
|
||||||
|
return login==null && encodedAuthorization==null;
|
||||||
|
}
|
||||||
|
|
||||||
/*package*/ void requireCredential() {
|
/*package*/ void requireCredential() {
|
||||||
if (login==null && encodedAuthorization==null)
|
if (isAnonymous())
|
||||||
throw new IllegalStateException("This operation requires a credential but none is given to the GitHub constructor");
|
throw new IllegalStateException("This operation requires a credential but none is given to the GitHub constructor");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -389,7 +398,7 @@ public class GitHub {
|
|||||||
|
|
||||||
static {
|
static {
|
||||||
MAPPER.setVisibilityChecker(new Std(NONE, NONE, NONE, NONE, ANY));
|
MAPPER.setVisibilityChecker(new Std(NONE, NONE, NONE, NONE, ANY));
|
||||||
MAPPER.getDeserializationConfig().set(Feature.FAIL_ON_UNKNOWN_PROPERTIES, false);
|
MAPPER.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static final String GITHUB_URL = "https://api.github.com";
|
private static final String GITHUB_URL = "https://api.github.com";
|
||||||
|
|||||||
38
src/main/java/org/kohsuke/github/GitUser.java
Normal file
38
src/main/java/org/kohsuke/github/GitUser.java
Normal file
@@ -0,0 +1,38 @@
|
|||||||
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Represents a user in Git who authors/commits a commit.
|
||||||
|
*
|
||||||
|
* In contrast, {@link GHUser} is an user of GitHub. Because Git allows a person to
|
||||||
|
* use multiple e-mail addresses and names when creating a commit, there's generally
|
||||||
|
* no meaningful mapping between {@link GHUser} and {@link GitUser}.
|
||||||
|
*
|
||||||
|
* @author Kohsuke Kawaguchi
|
||||||
|
*/
|
||||||
|
public class GitUser {
|
||||||
|
private String name, email, date;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Human readable name of the user, such as "Kohsuke Kawaguchi"
|
||||||
|
*/
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* E-mail address, such as "foo@example.com"
|
||||||
|
*/
|
||||||
|
public String getEmail() {
|
||||||
|
return email;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This field doesn't appear to be consistently available in all the situations where this class
|
||||||
|
* is used.
|
||||||
|
*/
|
||||||
|
public Date getDate() {
|
||||||
|
return GitHub.parseDate(date);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -25,6 +25,7 @@ package org.kohsuke.github;
|
|||||||
|
|
||||||
import org.apache.commons.io.IOUtils;
|
import org.apache.commons.io.IOUtils;
|
||||||
|
|
||||||
|
import javax.net.ssl.HttpsURLConnection;
|
||||||
import java.io.FileNotFoundException;
|
import java.io.FileNotFoundException;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
@@ -47,7 +48,7 @@ import java.util.NoSuchElementException;
|
|||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.zip.GZIPInputStream;
|
import java.util.zip.GZIPInputStream;
|
||||||
|
|
||||||
import static org.kohsuke.github.GitHub.*;
|
import static org.kohsuke.github.GitHub.MAPPER;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A builder pattern for making HTTP call and parsing its output.
|
* A builder pattern for making HTTP call and parsing its output.
|
||||||
@@ -62,6 +63,8 @@ class Requester {
|
|||||||
* Request method.
|
* Request method.
|
||||||
*/
|
*/
|
||||||
private String method = "POST";
|
private String method = "POST";
|
||||||
|
private String contentType = "application/x-www-form-urlencoded";
|
||||||
|
private InputStream body;
|
||||||
|
|
||||||
private static class Entry {
|
private static class Entry {
|
||||||
String key;
|
String key;
|
||||||
@@ -113,6 +116,11 @@ class Requester {
|
|||||||
return _with(key, value);
|
return _with(key, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Requester with(InputStream body) {
|
||||||
|
this.body = body;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
public Requester _with(String key, Object value) {
|
public Requester _with(String key, Object value) {
|
||||||
if (value!=null) {
|
if (value!=null) {
|
||||||
args.add(new Entry(key,value));
|
args.add(new Entry(key,value));
|
||||||
@@ -125,6 +133,11 @@ class Requester {
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Requester contentType(String contentType) {
|
||||||
|
this.contentType = contentType;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
public void to(String tailApiUrl) throws IOException {
|
public void to(String tailApiUrl) throws IOException {
|
||||||
to(tailApiUrl,null);
|
to(tailApiUrl,null);
|
||||||
}
|
}
|
||||||
@@ -162,13 +175,25 @@ class Requester {
|
|||||||
|
|
||||||
if (!method.equals("GET")) {
|
if (!method.equals("GET")) {
|
||||||
uc.setDoOutput(true);
|
uc.setDoOutput(true);
|
||||||
uc.setRequestProperty("Content-type","application/x-www-form-urlencoded");
|
uc.setRequestProperty("Content-type", contentType);
|
||||||
|
|
||||||
Map json = new HashMap();
|
if (body == null) {
|
||||||
for (Entry e : args) {
|
Map json = new HashMap();
|
||||||
json.put(e.key, e.value);
|
for (Entry e : args) {
|
||||||
|
json.put(e.key, e.value);
|
||||||
|
}
|
||||||
|
MAPPER.writeValue(uc.getOutputStream(), json);
|
||||||
|
} else {
|
||||||
|
try {
|
||||||
|
byte[] bytes = new byte[32768];
|
||||||
|
int read = 0;
|
||||||
|
while ((read = body.read(bytes)) != -1) {
|
||||||
|
uc.getOutputStream().write(bytes, 0, read);
|
||||||
|
}
|
||||||
|
} finally {
|
||||||
|
body.close();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
MAPPER.writeValue(uc.getOutputStream(),json);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
@@ -269,7 +294,7 @@ class Requester {
|
|||||||
|
|
||||||
|
|
||||||
private HttpURLConnection setupConnection(URL url) throws IOException {
|
private HttpURLConnection setupConnection(URL url) throws IOException {
|
||||||
HttpURLConnection uc = (HttpURLConnection) url.openConnection();
|
HttpsURLConnection uc = (HttpsURLConnection) url.openConnection();
|
||||||
|
|
||||||
// if the authentication is needed but no credential is given, try it anyway (so that some calls
|
// if the authentication is needed but no credential is given, try it anyway (so that some calls
|
||||||
// that do work with anonymous access in the reduced form should still work.)
|
// that do work with anonymous access in the reduced form should still work.)
|
||||||
|
|||||||
@@ -46,6 +46,9 @@ public class AppTest extends TestCase {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void testRepoCRUD() throws Exception {
|
public void testRepoCRUD() throws Exception {
|
||||||
|
GHRepository existing = gitHub.getMyself().getRepository("github-api-test");
|
||||||
|
if (existing!=null)
|
||||||
|
existing.delete();
|
||||||
GHRepository r = gitHub.createRepository("github-api-test", "a test repository", "http://github-api.kohsuke.org/", true);
|
GHRepository r = gitHub.createRepository("github-api-test", "a test repository", "http://github-api.kohsuke.org/", true);
|
||||||
r.enableIssueTracker(false);
|
r.enableIssueTracker(false);
|
||||||
r.enableDownloads(false);
|
r.enableDownloads(false);
|
||||||
@@ -79,6 +82,12 @@ public class AppTest extends TestCase {
|
|||||||
o.close();
|
o.close();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void testGetIssues() throws Exception {
|
||||||
|
List<GHIssue> closedIssues = gitHub.getUser("kohsuke").getRepository("github-api").getIssues(GHIssueState.CLOSED);
|
||||||
|
// prior to using PagedIterable GHRepository.getIssues(GHIssueState) would only retrieve 30 issues
|
||||||
|
assertTrue(closedIssues.size() > 30);
|
||||||
|
}
|
||||||
|
|
||||||
public void testRateLimit() throws IOException {
|
public void testRateLimit() throws IOException {
|
||||||
System.out.println(gitHub.getRateLimit());
|
System.out.println(gitHub.getRateLimit());
|
||||||
}
|
}
|
||||||
@@ -332,6 +341,12 @@ public class AppTest extends TestCase {
|
|||||||
assertEquals("oops!",state.getDescription());
|
assertEquals("oops!",state.getDescription());
|
||||||
assertEquals("http://jenkins-ci.org/",state.getTargetUrl());
|
assertEquals("http://jenkins-ci.org/",state.getTargetUrl());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void testCommitShortInfo() throws Exception {
|
||||||
|
GHCommit commit = gitHub.getUser("kohsuke").getRepository("test").getCommit("c77360d6f2ff2c2e6dd11828ad5dccf72419fa1b");
|
||||||
|
assertEquals(commit.getCommitShortInfo().getAuthor().getName(), "Kohsuke Kawaguchi");
|
||||||
|
assertEquals(commit.getCommitShortInfo().getMessage(), "Added a file");
|
||||||
|
}
|
||||||
|
|
||||||
public void testPullRequestPopulate() throws Exception {
|
public void testPullRequestPopulate() throws Exception {
|
||||||
GHRepository r = gitHub.getUser("kohsuke").getRepository("github-api");
|
GHRepository r = gitHub.getUser("kohsuke").getRepository("github-api");
|
||||||
|
|||||||
146
src/test/java/org/kohsuke/LifecycleTest.java
Normal file
146
src/test/java/org/kohsuke/LifecycleTest.java
Normal file
@@ -0,0 +1,146 @@
|
|||||||
|
package org.kohsuke;
|
||||||
|
|
||||||
|
import junit.framework.TestCase;
|
||||||
|
import org.apache.commons.io.IOUtils;
|
||||||
|
import org.eclipse.jgit.api.Git;
|
||||||
|
import org.eclipse.jgit.api.errors.GitAPIException;
|
||||||
|
import org.eclipse.jgit.dircache.DirCache;
|
||||||
|
import org.eclipse.jgit.transport.UsernamePasswordCredentialsProvider;
|
||||||
|
import org.kohsuke.github.GHAsset;
|
||||||
|
import org.kohsuke.github.GHIssue;
|
||||||
|
import org.kohsuke.github.GHMilestone;
|
||||||
|
import org.kohsuke.github.GHMyself;
|
||||||
|
import org.kohsuke.github.GHRelease;
|
||||||
|
import org.kohsuke.github.GHRepository;
|
||||||
|
import org.kohsuke.github.GitHub;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.FileInputStream;
|
||||||
|
import java.io.FileWriter;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.PrintWriter;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Properties;
|
||||||
|
|
||||||
|
public class LifecycleTest extends TestCase {
|
||||||
|
private GitHub gitHub;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setUp() throws Exception {
|
||||||
|
super.setUp();
|
||||||
|
gitHub = GitHub.connect();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testCreateRepository() throws IOException, GitAPIException {
|
||||||
|
GHMyself myself = gitHub.getMyself();
|
||||||
|
GHRepository repository = myself.getRepository("github-api-test");
|
||||||
|
if (repository != null) {
|
||||||
|
repository.delete();
|
||||||
|
}
|
||||||
|
repository = gitHub.createRepository("github-api-test",
|
||||||
|
"a test repository used to test kohsuke's github-api", "http://github-api.kohsuke.org/", true);
|
||||||
|
|
||||||
|
assertTrue(repository.getReleases().isEmpty());
|
||||||
|
try {
|
||||||
|
GHMilestone milestone = repository.createMilestone("Initial Release", "first one");
|
||||||
|
GHIssue issue = repository.createIssue("Test Issue")
|
||||||
|
.body("issue body just for grins")
|
||||||
|
.milestone(milestone)
|
||||||
|
.assignee(myself)
|
||||||
|
.label("bug")
|
||||||
|
.create();
|
||||||
|
File repoDir = new File(System.getProperty("java.io.tmpdir"), "github-api-test");
|
||||||
|
delete(repoDir);
|
||||||
|
Git origin = Git.cloneRepository()
|
||||||
|
.setBare(false)
|
||||||
|
.setURI(repository.gitHttpTransportUrl())
|
||||||
|
.setDirectory(repoDir)
|
||||||
|
.setCredentialsProvider(getCredentialsProvider(myself))
|
||||||
|
.call();
|
||||||
|
|
||||||
|
commitTestFile(myself, repoDir, origin);
|
||||||
|
|
||||||
|
|
||||||
|
GHRelease release = createRelease(repository);
|
||||||
|
|
||||||
|
GHAsset asset = uploadAsset(release);
|
||||||
|
|
||||||
|
updateAsset(release, asset);
|
||||||
|
|
||||||
|
deleteAsset(release, asset);
|
||||||
|
} finally {
|
||||||
|
repository.delete();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void updateAsset(GHRelease release, GHAsset asset) throws IOException {
|
||||||
|
asset.setLabel("test label");
|
||||||
|
assertEquals("test label", release.getAssets().get(0).getLabel());
|
||||||
|
}
|
||||||
|
|
||||||
|
private void deleteAsset(GHRelease release, GHAsset asset) throws IOException {
|
||||||
|
asset.delete();
|
||||||
|
assertEquals(0, release.getAssets().size());
|
||||||
|
}
|
||||||
|
|
||||||
|
private GHAsset uploadAsset(GHRelease release) throws IOException {
|
||||||
|
GHAsset asset = release.uploadAsset(new File("pom.xml"), "application/text");
|
||||||
|
assertNotNull(asset);
|
||||||
|
List<GHAsset> assets = release.getAssets();
|
||||||
|
assertEquals(1, assets.size());
|
||||||
|
assertEquals("pom.xml", assets.get(0).getName());
|
||||||
|
|
||||||
|
return asset;
|
||||||
|
}
|
||||||
|
|
||||||
|
private GHRelease createRelease(GHRepository repository) throws IOException {
|
||||||
|
GHRelease builder = repository.createRelease("release_tag")
|
||||||
|
.name("Test Release")
|
||||||
|
.body("How exciting! To be able to programmatically create releases is a dream come true!")
|
||||||
|
.create();
|
||||||
|
List<GHRelease> releases = repository.getReleases();
|
||||||
|
assertEquals(1, releases.size());
|
||||||
|
GHRelease release = releases.get(0);
|
||||||
|
assertEquals("Test Release", release.getName());
|
||||||
|
return release;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void commitTestFile(GHMyself myself, File repoDir, Git origin) throws IOException, GitAPIException {
|
||||||
|
File dummyFile = createDummyFile(repoDir);
|
||||||
|
DirCache cache = origin.add().addFilepattern(dummyFile.getName()).call();
|
||||||
|
origin.commit().setMessage("test commit").call();
|
||||||
|
origin.push().setCredentialsProvider(getCredentialsProvider(myself)).call();
|
||||||
|
}
|
||||||
|
|
||||||
|
private UsernamePasswordCredentialsProvider getCredentialsProvider(GHMyself myself) throws IOException {
|
||||||
|
Properties props = new Properties();
|
||||||
|
File homeDir = new File(System.getProperty("user.home"));
|
||||||
|
FileInputStream in = new FileInputStream(new File(homeDir, ".github"));
|
||||||
|
try {
|
||||||
|
props.load(in);
|
||||||
|
} finally {
|
||||||
|
IOUtils.closeQuietly(in);
|
||||||
|
}
|
||||||
|
return new UsernamePasswordCredentialsProvider(props.getProperty("login"), props.getProperty("oauth"));
|
||||||
|
}
|
||||||
|
|
||||||
|
private void delete(File toDelete) {
|
||||||
|
if (toDelete.isDirectory()) {
|
||||||
|
for (File file : toDelete.listFiles()) {
|
||||||
|
delete(file);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
toDelete.delete();
|
||||||
|
}
|
||||||
|
|
||||||
|
private File createDummyFile(File repoDir) throws IOException {
|
||||||
|
File file = new File(repoDir, "testFile-" + System.currentTimeMillis());
|
||||||
|
PrintWriter writer = new PrintWriter(new FileWriter(file));
|
||||||
|
try {
|
||||||
|
writer.println("test file");
|
||||||
|
} finally {
|
||||||
|
writer.close();
|
||||||
|
}
|
||||||
|
return file;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,67 @@
|
|||||||
|
package org.kohsuke.github;
|
||||||
|
|
||||||
|
import junit.framework.TestCase;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.UUID;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Integration test for {@link GHContent}.
|
||||||
|
*/
|
||||||
|
public class GHContentIntegrationTest extends TestCase {
|
||||||
|
|
||||||
|
private GitHub gitHub;
|
||||||
|
private GHRepository repo;
|
||||||
|
private String createdFilename;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setUp() throws Exception {
|
||||||
|
super.setUp();
|
||||||
|
|
||||||
|
gitHub = GitHub.connect();
|
||||||
|
repo = gitHub.getRepository("acollign/github-api-test").fork();
|
||||||
|
createdFilename = UUID.randomUUID().toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testGetFileContent() throws Exception {
|
||||||
|
GHContent content = repo.getFileContent("ghcontent-ro/a-file-with-content");
|
||||||
|
|
||||||
|
assertTrue(content.isFile());
|
||||||
|
assertEquals("thanks for reading me\n", content.getContent());
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testGetEmptyFileContent() throws Exception {
|
||||||
|
GHContent content = repo.getFileContent("ghcontent-ro/an-empty-file");
|
||||||
|
|
||||||
|
assertTrue(content.isFile());
|
||||||
|
assertEquals("", content.getContent());
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testGetDirectoryContent() throws Exception {
|
||||||
|
List<GHContent> entries = repo.getDirectoryContent("ghcontent-ro/a-dir-with-3-entries");
|
||||||
|
|
||||||
|
assertTrue(entries.size() == 3);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testCRUDContent() throws Exception {
|
||||||
|
GHContentUpdateResponse created = repo.createContent("this is an awesome file I created\n", "Creating a file for integration tests.", createdFilename);
|
||||||
|
GHContent createdContent = created.getContent();
|
||||||
|
|
||||||
|
assertNotNull(created.getCommit());
|
||||||
|
assertNotNull(created.getContent());
|
||||||
|
assertNotNull(createdContent.getContent());
|
||||||
|
assertEquals("this is an awesome file I created\n", createdContent.getContent());
|
||||||
|
|
||||||
|
GHContentUpdateResponse updatedContentResponse = createdContent.update("this is some new content\n", "Updated file for integration tests.");
|
||||||
|
GHContent updatedContent = updatedContentResponse.getContent();
|
||||||
|
|
||||||
|
assertNotNull(updatedContentResponse.getCommit());
|
||||||
|
assertNotNull(updatedContentResponse.getContent());
|
||||||
|
assertEquals("this is some new content\n", updatedContent.getContent());
|
||||||
|
|
||||||
|
GHContentUpdateResponse deleteResponse = updatedContent.delete("Enough of this foolishness!");
|
||||||
|
|
||||||
|
assertNotNull(deleteResponse.getCommit());
|
||||||
|
assertNull(deleteResponse.getContent());
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user