From 1f3b8866e72e202f7f02edafa7194a9b1a93d101 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Thu, 9 Dec 2010 10:00:54 -0800 Subject: [PATCH] added support for repository commit hook access --- .../java/org/kohsuke/github/GHException.java | 14 +++ .../java/org/kohsuke/github/GHRepository.java | 114 +++++++++++++++++- src/test/java/org/kohsuke/AppTest.java | 23 +++- 3 files changed, 147 insertions(+), 4 deletions(-) create mode 100644 src/main/java/org/kohsuke/github/GHException.java diff --git a/src/main/java/org/kohsuke/github/GHException.java b/src/main/java/org/kohsuke/github/GHException.java new file mode 100644 index 000000000..c238e53c9 --- /dev/null +++ b/src/main/java/org/kohsuke/github/GHException.java @@ -0,0 +1,14 @@ +package org.kohsuke.github; + +/** + * @author Kohsuke Kawaguchi + */ +public class GHException extends RuntimeException { + public GHException(String message) { + super(message); + } + + public GHException(String message, Throwable cause) { + super(message, cause); + } +} diff --git a/src/main/java/org/kohsuke/github/GHRepository.java b/src/main/java/org/kohsuke/github/GHRepository.java index 116b454b3..c1c7c25d1 100644 --- a/src/main/java/org/kohsuke/github/GHRepository.java +++ b/src/main/java/org/kohsuke/github/GHRepository.java @@ -23,14 +23,23 @@ */ package org.kohsuke.github; +import com.gargoylesoftware.htmlunit.WebClient; +import com.gargoylesoftware.htmlunit.html.HtmlForm; +import com.gargoylesoftware.htmlunit.html.HtmlInput; +import com.gargoylesoftware.htmlunit.html.HtmlPage; + import java.io.IOException; import java.net.URL; +import java.util.AbstractSet; +import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.HashSet; +import java.util.Iterator; +import java.util.List; import java.util.Set; -import static java.util.Arrays.asList; +import static java.util.Arrays.*; /** * A repository on GitHub. @@ -52,6 +61,9 @@ public class GHRepository { return homepage; } + /** + * URL of this repository, like 'http://github.com/kohsuke/hudson' + */ public String getUrl() { return url; } @@ -154,6 +166,106 @@ public class GHRepository { throw new IOException("Operation not applicable to a repository owned by someone else: "+owner); } + /** + * Returns a set that represents the post-commit hook URLs. + * The returned set is live, and changes made to them are reflected to GitHub. + */ + public Set getPostCommitHooks() { + return postCommitHooks; + } + + /** + * Live set view of the post-commit hook. + */ + private final Set postCommitHooks = new AbstractSet() { + private List getPostCommitHooks() { + try { + verifyMine(); + + HtmlForm f = getForm(); + + List r = new ArrayList(); + for (HtmlInput i : f.getInputsByName("urls[]")) { + String v = i.getValueAttribute(); + if (v.length()==0) continue; + r.add(new URL(v)); + } + return r; + } catch (IOException e) { + throw new GHException("Failed to retrieve post-commit hooks",e); + } + } + + @Override + public Iterator iterator() { + return getPostCommitHooks().iterator(); + } + + @Override + public int size() { + return getPostCommitHooks().size(); + } + + @Override + public boolean add(URL url) { + try { + String u = url.toExternalForm(); + + verifyMine(); + + HtmlForm f = getForm(); + + List controls = f.getInputsByName("urls[]"); + for (HtmlInput i : controls) { + String v = i.getValueAttribute(); + if (v.length()==0) continue; + if (v.equals(u)) + return false; // already there + } + + controls.get(controls.size()-1).setValueAttribute(u); + f.submit(null); + return true; + } catch (IOException e) { + throw new GHException("Failed to update post-commit hooks",e); + } + } + + @Override + public boolean remove(Object o) { + try { + String u = ((URL)o).toExternalForm(); + + verifyMine(); + + HtmlForm f = getForm(); + + List controls = f.getInputsByName("urls[]"); + for (HtmlInput i : controls) { + String v = i.getValueAttribute(); + if (v.length()==0) continue; + if (v.equals(u)) { + i.setValueAttribute(""); + f.submit(null); + return true; + } + } + + return false; + } catch (IOException e) { + throw new GHException("Failed to update post-commit hooks",e); + } + } + + private HtmlForm getForm() throws IOException { + WebClient wc = root.createWebClient(); + HtmlPage pg = (HtmlPage)wc.getPage(getUrl()+"/admin"); + HtmlForm f = (HtmlForm) pg.getElementById("new_service"); + return f; + } + }; + + @Override public String toString() { return "Repository:"+owner+":"+name; diff --git a/src/test/java/org/kohsuke/AppTest.java b/src/test/java/org/kohsuke/AppTest.java index 84ba0d6d8..32cbb3edb 100644 --- a/src/test/java/org/kohsuke/AppTest.java +++ b/src/test/java/org/kohsuke/AppTest.java @@ -9,6 +9,8 @@ import org.kohsuke.github.GHTeam; import org.kohsuke.github.GitHub; import java.io.IOException; +import java.net.URL; +import java.util.Set; /** * Unit test for simple App. @@ -16,10 +18,9 @@ import java.io.IOException; public class AppTest extends TestCase { public void testApp() throws IOException { GitHub gitHub = GitHub.connect(); - GHOrganization labs = gitHub.getOrganization("HudsonLabs"); - GHTeam t = labs.getTeams().get("Core Developers"); +// testOrganization(gitHub); - t.add(labs.getRepository("xyz")); + testPostCommitHook(gitHub); // t.add(gitHub.getMyself()); // System.out.println(t.getMembers()); @@ -35,4 +36,20 @@ public class AppTest extends TestCase { // // System.out.println(hub.getUser("kohsuke").getRepository("hudson").getCollaborators()); } + + private void testPostCommitHook(GitHub gitHub) throws IOException { + GHRepository r = gitHub.getMyself().getRepository("foo"); + Set hooks = r.getPostCommitHooks(); + hooks.add(new URL("http://kohsuke.org/test")); + System.out.println(hooks); + hooks.remove(new URL("http://kohsuke.org/test")); + System.out.println(hooks); + } + + private void testOrganization(GitHub gitHub) throws IOException { + GHOrganization labs = gitHub.getOrganization("HudsonLabs"); + GHTeam t = labs.getTeams().get("Core Developers"); + + t.add(labs.getRepository("xyz")); + } }