Skip to content

Commit

Permalink
Fix matrix builds with multiple SCMs
Browse files Browse the repository at this point in the history
This fixes a bug that causes Matrix Builds to fail when using two or
more Mercurial repositories (via the multiple-scms plugin).

Previously, each SCM tried to checkout the changeset from the first
Mercurial repository.  This checks for the presence of the
multiple-scms plugin and, if the build uses it, looks up the parent
changeset using multiple-scms.

I also modified the MatrixBuild tests to fail faster when builds fail
(added an await timeout).

JENKINS-18237
  • Loading branch information
blt04 committed Feb 18, 2014
1 parent 5dabef8 commit 1a33ebc
Show file tree
Hide file tree
Showing 2 changed files with 48 additions and 2 deletions.
15 changes: 14 additions & 1 deletion src/main/java/hudson/plugins/mercurial/MercurialSCM.java
Expand Up @@ -43,6 +43,7 @@
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import net.sf.json.JSONObject;
import org.jenkinsci.plugins.multiplescms.MultiSCMRevisionState;
import org.kohsuke.stapler.AncestorInPath;
import org.kohsuke.stapler.DataBoundConstructor;
import org.kohsuke.stapler.QueryParameter;
Expand Down Expand Up @@ -645,7 +646,19 @@ private String getRevToBuild(AbstractBuild<?, ?> build, EnvVars env) {
String revToBuild = getRevision(env);
if (build instanceof MatrixRun) {
MatrixRun matrixRun = (MatrixRun) build;
MercurialTagAction parentRevision = matrixRun.getParentBuild().getAction(MercurialTagAction.class);
MercurialTagAction parentRevision;

if (Hudson.getInstance().getPlugin("multiple-scms") != null) {
MultiSCMRevisionState parentRevisions = matrixRun.getParentBuild().getAction(MultiSCMRevisionState.class);
if (parentRevisions != null) {
parentRevision = (MercurialTagAction) parentRevisions.get(this, build.getWorkspace(), build);
} else {
parentRevision = matrixRun.getParentBuild().getAction(MercurialTagAction.class);
}
} else {
parentRevision = matrixRun.getParentBuild().getAction(MercurialTagAction.class);
}

if (parentRevision != null && parentRevision.getId() != null) {
revToBuild = parentRevision.getId();
}
Expand Down
35 changes: 34 additions & 1 deletion src/test/java/hudson/plugins/mercurial/MatrixProjectTest.java
Expand Up @@ -4,6 +4,7 @@
import hudson.Proc;
import hudson.matrix.*;
import hudson.model.*;
import hudson.scm.SCM;
import org.jvnet.hudson.test.FakeLauncher;
import org.jvnet.hudson.test.PretendSlave;
import org.jvnet.hudson.test.TestBuilder;
Expand All @@ -13,11 +14,14 @@
import java.util.*;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.Future;
import java.util.concurrent.TimeUnit;
import org.jenkinsci.plugins.multiplescms.MultiSCM;
import static org.junit.Assert.*;
import org.junit.Before;
import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.TemporaryFolder;
import org.jvnet.hudson.test.Bug;
import org.jvnet.hudson.test.JenkinsRule;

public class MatrixProjectTest {
Expand All @@ -27,6 +31,7 @@ public class MatrixProjectTest {
@Rule public TemporaryFolder tmp = new TemporaryFolder();
@Rule public TemporaryFolder tmp2 = new TemporaryFolder();
private File repo;
private File repo2;
private MatrixProject matrixProject;

@Before public void setUp() throws Exception {
Expand All @@ -43,6 +48,17 @@ public class MatrixProjectTest {
m.touchAndCommit(repo, "a");
}

private void setUpMultiSCM() throws Exception {
repo2 = tmp.newFolder();

matrixProject.setScm(new MultiSCM(Arrays.<SCM>asList(
new MercurialSCM(null, repo2.getPath(), null, null, "r2", null, false),
new MercurialSCM(null, repo.getPath(), null, null, "r1", null, false))));

m.hg(repo2, "init");
m.touchAndCommit(repo2, "r2f1");
}

@Test public void allRunsBuildSameRevisionOnClone() throws Exception {
assertAllMatrixRunsBuildSameMercurialRevision();
}
Expand All @@ -55,6 +71,23 @@ public class MatrixProjectTest {
assertAllMatrixRunsBuildSameMercurialRevision();
}

@Bug(18237)
@Test public void multiSCMRunsBuildSameRevisionOnClone() throws Exception {
setUpMultiSCM();
assertAllMatrixRunsBuildSameMercurialRevision();
}

@Bug(18237)
@Test public void multiSCMRunsBuildSameRevisionOnUpdate() throws Exception {
setUpMultiSCM();

//schedule an initial build, to test update behavior later in the test
j.assertBuildStatusSuccess(matrixProject.scheduleBuild2(0));
m.touchAndCommit(repo, "ab");

assertAllMatrixRunsBuildSameMercurialRevision();
}

private void assertAllMatrixRunsBuildSameMercurialRevision() throws Exception {
//set the second slave offline, to give us the opportunity to push changes to the original Mercurial repository
//between the scheduling of the build and the actual run.
Expand All @@ -72,7 +105,7 @@ public boolean perform(AbstractBuild<?, ?> build, Launcher launcher, BuildListen
});

Future<MatrixBuild> matrixBuildFuture = matrixProject.scheduleBuild2(0);
firstBuild.await();
firstBuild.await(5, TimeUnit.SECONDS);

//push an extra commit to the central repository
m.touchAndCommit(repo, "b");
Expand Down

0 comments on commit 1a33ebc

Please sign in to comment.