Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
[JENKINS-10255] Add more tests for polling, and fix a bug with the ne…
…w polling when multiple changesets are involved.
  • Loading branch information
davidmc24 committed Oct 17, 2011
1 parent 3a27ed7 commit d50764a
Show file tree
Hide file tree
Showing 4 changed files with 110 additions and 23 deletions.
9 changes: 5 additions & 4 deletions src/main/java/hudson/plugins/mercurial/MercurialSCM.java
Expand Up @@ -282,14 +282,14 @@ protected PollingResult compareRemoteRevisionWith(AbstractProject<?, ?> project,

ArgumentListBuilder logCmd = findHgExe(node, listener, false);
logCmd.add("log", "--style", tmpFile.getRemote());
logCmd.add("--rev", ".:" + getBranch(), "--branch", getBranch());
logCmd.add("--prune", ".");
logCmd.add("--branch", getBranch());

This comment has been minimized.

Copy link
@willemv

willemv Dec 13, 2011

Contributor

This commit loses important functionality: if you commit on another named branch (say, a bug fix on BRANCH_V9), and then merge that commit to the configure branch (say, BRANCH_V10), a build will no longer be triggered now, even tough something significant did change.

Previously, the commit on BRANCH_V9 was picked up by jenkins.

This comment has been minimized.

Copy link
@jglick

jglick Dec 13, 2011

Member

Best to file a fresh bug report for such a regression so it does not get forgotten.

This comment has been minimized.

Copy link
@willemv

willemv Dec 13, 2011

Contributor

The comment is on the wrong commit even, I've introduced this bug in c148799. I'll file a JIRA issue and fix it somewhere this week.

logCmd.add("--no-merges");

ByteArrayOutputStream baos = new ByteArrayOutputStream();
ForkOutputStream fos = new ForkOutputStream(baos, output);

if (forest) {
logCmd.add("--prune", ".");
StringTokenizer trees = new StringTokenizer(hg.popen(repository, listener, false, new ArgumentListBuilder("ftrees", "--convert")));
while (trees.hasMoreTokens()) {
String tree = trees.nextToken();
Expand All @@ -298,12 +298,13 @@ protected PollingResult compareRemoteRevisionWith(AbstractProject<?, ?> project,
true, listener);
}
} else {
logCmd.add("--prune", baseline.id);
joinWithPossibleTimeout(
launch(launcher).cmds(logCmd).stdout(fos).pwd(repository),
true, listener);
}

MercurialTagAction cur = parseIncomingOutput(baos, baseline, changedFileNames);
MercurialTagAction cur = parsePollingLogOutput(baos, baseline, changedFileNames);
return new PollingResult(baseline,cur,computeDegreeOfChanges(changedFileNames,output));
} finally {
tmpFile.delete();
Expand Down Expand Up @@ -371,7 +372,7 @@ private Set<String> dependentChanges(Set<String> changedFileNames) {

private static Pattern FILES_LINE = Pattern.compile("files:(.*)");

private MercurialTagAction parseIncomingOutput(ByteArrayOutputStream output, MercurialTagAction baseline, Set<String> result) throws IOException {
private MercurialTagAction parsePollingLogOutput(ByteArrayOutputStream output, MercurialTagAction baseline, Set<String> result) throws IOException {
String headId = null; // the tip of the remote revision
BufferedReader in = new BufferedReader(new InputStreamReader(
new ByteArrayInputStream(output.toByteArray())));
Expand Down
4 changes: 2 additions & 2 deletions src/test/java/hudson/plugins/mercurial/ForestTest.java
Expand Up @@ -26,7 +26,7 @@ public void testCloneAndClean() throws Exception {
touchAndCommit(toprepo, "a");
touchAndCommit(subrepo, "b");
FreeStyleProject p = createFreeStyleProject();
p.setScm(new MercurialSCM("forested" ,toprepo.getPath(), null, null, null, null, true, true));
p.setScm(new MercurialSCM("forested", toprepo.getPath(), null, null, null, null, true, true));
buildAndCheck(p, "sub/b");
FilePath ws = p.getSomeWorkspace();
ws.child("junk").touch(0);
Expand All @@ -35,7 +35,7 @@ public void testCloneAndClean() throws Exception {
assertFalse(ws.child("junk").exists());
assertFalse(ws.child("sub/trash").exists());
touchAndCommit(subrepo, "more");
assertTrue(pollSCMChanges(p));
assertTrue(pollSCMChanges(p).hasChanges());
buildAndCheck(p, "sub/more");
}

Expand Down
100 changes: 85 additions & 15 deletions src/test/java/hudson/plugins/mercurial/MercurialSCMTest.java
Expand Up @@ -8,6 +8,8 @@
import hudson.model.ParametersAction;
import hudson.model.StringParameterValue;
import hudson.scm.ChangeLogSet;
import hudson.scm.PollingResult;

import java.io.File;
import java.io.IOException;
import java.util.*;
Expand Down Expand Up @@ -53,35 +55,38 @@ public void testBranches() throws Exception {
hg(repo, "update", "--clean", "default");
touchAndCommit(repo, "default-2");
// Changes in default should be ignored.
assertFalse(pollSCMChanges(p));
assertFalse(pollSCMChanges(p).hasChanges());
hg(repo, "update", "--clean", "b");
touchAndCommit(repo, "b-2");
// But changes in b should be pulled.
assertTrue(pollSCMChanges(p));
assertTrue(pollSCMChanges(p).hasChanges());
buildAndCheck(p, "b-2");
// Switch to default branch with an existing workspace.
p.setScm(new MercurialSCM(hgInstallation, repo.getPath(), null, null, null, null, false, false));
// Should now consider preexisting changesets in default to be poll triggers.
assertTrue(pollSCMChanges(p));
assertTrue(pollSCMChanges(p).hasChanges());
// Should switch working copy to default branch.
buildAndCheck(p, "default-2");
touchAndCommit(repo, "b-3");
// Changes in other branch should be ignored.
assertFalse(pollSCMChanges(p));
assertFalse(pollSCMChanges(p).hasChanges());
}

@Bug(1099)
public void testPollingLimitedToModules() throws Exception {
PollingResult pr;
FreeStyleProject p = createFreeStyleProject();
p.setScm(new MercurialSCM(hgInstallation, repo.getPath(), null, "dir1 dir2", null, null, false, false));
hg(repo, "init");
touchAndCommit(repo, "dir1/f");
buildAndCheck(p, "dir1/f");
touchAndCommit(repo, "dir2/f");
assertTrue(pollSCMChanges(p));
pr = pollSCMChanges(p);
assertEquals(PollingResult.Change.SIGNIFICANT, pr.change);
buildAndCheck(p, "dir2/f");
touchAndCommit(repo, "dir3/f");
assertFalse(pollSCMChanges(p));
pr = pollSCMChanges(p);
assertEquals(PollingResult.Change.INSIGNIFICANT, pr.change);
// No support for partial checkouts yet, so workspace will contain everything.
buildAndCheck(p, "dir3/f");
// HUDSON-4972: do not pay attention to merges
Expand All @@ -92,22 +97,26 @@ public void testPollingLimitedToModules() throws Exception {
hg(repo, "merge");
new FilePath(repo).child("dir2/f").write("stuff", "UTF-8");
hg(repo, "commit", "--message", "merged");
assertFalse(pollSCMChanges(p));
pr = pollSCMChanges(p);
assertEquals(PollingResult.Change.INSIGNIFICANT, pr.change);
buildAndCheck(p, "dir4/f");
}

@Bug(6337)
public void testPollingLimitedToModules2() throws Exception {
PollingResult pr;
FreeStyleProject p = createFreeStyleProject();
p.setScm(new MercurialSCM(hgInstallation, repo.getPath(), null, "dir1", null, null, false, false));
hg(repo, "init");
touchAndCommit(repo, "starter");
pollSCMChanges(p);
buildAndCheck(p, "starter");
touchAndCommit(repo, "dir2/f");
assertFalse(pollSCMChanges(p));
pr = pollSCMChanges(p);
assertEquals(PollingResult.Change.INSIGNIFICANT, pr.change);
touchAndCommit(repo, "dir1/f");
assertTrue(pollSCMChanges(p));
pr = pollSCMChanges(p);
assertEquals(PollingResult.Change.SIGNIFICANT, pr.change);
buildAndCheck(p, "dir1/f");
}

Expand Down Expand Up @@ -222,24 +231,24 @@ public void testMultipleProjectsForSingleSource() throws Exception {

hg(repo, "init");
touchAndCommit(repo, "f1");
assertTrue(pollSCMChanges(one));
assertTrue(pollSCMChanges(one).hasChanges());
buildAndCheck(one, "f1");
assertTrue(pollSCMChanges(two));
assertTrue(pollSCMChanges(two).hasChanges());

hg(repo, "branch", "b");
touchAndCommit(repo, "b1");

assertFalse(pollSCMChanges(one));
assertFalse(pollSCMChanges(one).hasChanges());

buildAndCheck(three, "b1");
buildAndCheck(four, "b1");

touchAndCommit(repo, "b2");
assertTrue(pollSCMChanges(three));
assertTrue(pollSCMChanges(three).hasChanges());
buildAndCheck(three, "b2");
assertTrue(pollSCMChanges(four));
assertTrue(pollSCMChanges(four).hasChanges());

assertFalse(pollSCMChanges(one));
assertFalse(pollSCMChanges(one).hasChanges());
}

/**
Expand Down Expand Up @@ -319,6 +328,49 @@ public void testChangelogFromPreviousBuild() throws Exception {
assertChangeSetPaths(Collections.singletonList(Collections.singleton("dir3/f1")), b);
}

public void testPolling() throws Exception {
AbstractBuild<?, ?> b;
PollingResult pr;
FreeStyleProject p = createFreeStyleProject();
p.setScm(new MercurialSCM(hgInstallation, repo.getPath(), null, null, null, null, false, false));
p.setAssignedLabel(null); // Allow roaming

// No builds, no workspace, but an available remote repository
hg(repo, "init");
touchAndCommit(repo, "f1");
String cs1 = getLastChangesetId(repo);
pr = pollSCMChanges(p);
assertPollingResult(PollingResult.Change.INCOMPARABLE, null, null, pr);

// We have a workspace, and no new changes in remote repository
b = p.scheduleBuild2(0).get();
pr = pollSCMChanges(p);
assertPollingResult(PollingResult.Change.NONE, cs1, cs1, pr);

// We have a workspace, and new changes in the remote repository
touchAndCommit(repo, "f2");
String cs2 = getLastChangesetId(repo);
pr = pollSCMChanges(p);
assertPollingResult(PollingResult.Change.SIGNIFICANT, cs1, cs2, pr);

// We lost the workspace
b.getWorkspace().deleteRecursive();
pr = pollSCMChanges(p);
assertPollingResult(PollingResult.Change.INCOMPARABLE, null, null, pr);
b = p.scheduleBuild2(0).get();

// Multiple polls
touchAndCommit(repo, "f3");
touchAndCommit(repo, "f4");
String cs4 = getLastChangesetId(repo);
pr = pollSCMChanges(p);
assertPollingResult(PollingResult.Change.SIGNIFICANT, cs2, cs4, pr);
touchAndCommit(repo, "f5");
String cs5 = getLastChangesetId(repo);
pr = pollSCMChanges(p);
assertPollingResult(PollingResult.Change.SIGNIFICANT, cs4, cs5, pr);
}

private PretendSlave createNoopPretendSlave() throws Exception {
return createPretendSlave(new NoopFakeLauncher());
}
Expand All @@ -332,6 +384,24 @@ private void assertChangeSetPaths(List<Set<String>> expectedChangeSetPaths, Abst
assertEquals(expectedChangeSetPaths, actualChangeSetPaths);
}

private void assertPollingResult(PollingResult.Change expectedChangeDegree, String expectedBaselineId, String expectedRemoteId, PollingResult actualPollingResult) {
assertNotNull(actualPollingResult);
PollingResult.Change actualChangeDegree = actualPollingResult.change;
assertEquals(expectedChangeDegree, actualChangeDegree);
if(expectedBaselineId == null) {
assertNull(actualPollingResult.baseline);
} else {
MercurialTagAction actualBaseline = (MercurialTagAction) actualPollingResult.baseline;
assertEquals(expectedBaselineId, actualBaseline.id);
}
if(expectedRemoteId == null) {
assertNull(actualPollingResult.remote);
} else {
MercurialTagAction actualRemote = (MercurialTagAction) actualPollingResult.remote;
assertEquals(expectedRemoteId, actualRemote.id);
}
}

private static final class NoopFakeLauncher implements FakeLauncher {
public Proc onLaunch(Launcher.ProcStarter p) throws IOException {
return null;
Expand Down
20 changes: 18 additions & 2 deletions src/test/java/hudson/plugins/mercurial/MercurialTestCase.java
Expand Up @@ -8,7 +8,10 @@
import hudson.model.FreeStyleProject;
import hudson.model.Hudson;
import hudson.model.TaskListener;
import hudson.scm.PollingResult;
import hudson.util.StreamTaskListener;

import java.io.ByteArrayOutputStream;
import java.io.File;
import java.nio.charset.Charset;
import java.util.ArrayList;
Expand Down Expand Up @@ -66,8 +69,21 @@ protected String buildAndCheck(FreeStyleProject p, String name, Action... action
return log;
}

protected boolean pollSCMChanges(FreeStyleProject p) {
return p.poll(new StreamTaskListener(System.out, Charset.defaultCharset())).hasChanges();
protected PollingResult pollSCMChanges(FreeStyleProject p) {
return p.poll(new StreamTaskListener(System.out, Charset.defaultCharset()));
}

protected String getLastChangesetId(File repo) throws Exception {
List<String> cmds = new ArrayList<String>();
cmds.add("hg");
cmds.add("log");
cmds.add("-l1");
cmds.add("--template");
cmds.add("{node}");
ByteArrayOutputStream baos = new ByteArrayOutputStream();
TaskListener nodeListener = new StreamTaskListener(baos);
assertEquals(0, MercurialSCM.launch(launcher).cmds(cmds).pwd(repo).stdout(nodeListener).stderr(baos).join());
return baos.toString();
}

}

0 comments on commit d50764a

Please sign in to comment.