diff --git a/src/main/java/com/sonyericsson/rebuild/RebuildAction.java b/src/main/java/com/sonyericsson/rebuild/RebuildAction.java index 605f3a2..31fbb85 100644 --- a/src/main/java/com/sonyericsson/rebuild/RebuildAction.java +++ b/src/main/java/com/sonyericsson/rebuild/RebuildAction.java @@ -24,6 +24,7 @@ */ package com.sonyericsson.rebuild; +import com.google.common.collect.*; import hudson.Extension; import hudson.model.Action; @@ -32,6 +33,8 @@ import java.io.IOException; import java.util.ArrayList; import java.util.List; +import java.util.Set; +import java.util.Comparator; import hudson.matrix.MatrixRun; import hudson.model.BooleanParameterValue; @@ -57,9 +60,6 @@ import org.kohsuke.stapler.StaplerRequest; import org.kohsuke.stapler.StaplerResponse; -import com.sonyericsson.rebuild.RebuildParameterPage; -import com.sonyericsson.rebuild.RebuildParameterProvider; - /** * Rebuild RootAction implementation class. This class will basically reschedule * the build with existing parameters. @@ -297,7 +297,13 @@ public void doConfigSubmit(StaplerRequest req, StaplerResponse rsp) throws Servl } } - List actions = constructRebuildCause(build, new ParametersAction(values)); + Set mergedValues = ImmutableSortedSet.copyOf(new Comparator() { + @Override + public int compare(ParameterValue o1, ParameterValue o2) { + return o1.getName().compareTo(o2.getName()); + } + }, Iterables.concat(values, paramAction == null ? new ArrayList() : paramAction.getParameters())); + List actions = constructRebuildCause(build, new ParametersAction(Lists.newArrayList(mergedValues))); Hudson.getInstance().getQueue().schedule((Queue.Task) build.getParent(), 0, actions); rsp.sendRedirect("../../"); @@ -361,14 +367,14 @@ public boolean isRebuildAvailable() { && project.hasPermission(Item.BUILD) && project.isBuildable() && project instanceof Queue.Task - && !isMatrixRun() + && !isMatrixRun() && !isRebuildDisbaled(); } private boolean isRebuildDisbaled() { RebuildSettings settings = (RebuildSettings)getProject().getProperty(RebuildSettings.class); - + if (settings != null && settings.getRebuildDisabled()) { return true; } diff --git a/src/test/java/com/sonyericsson/rebuild/RebuildValidatorTest.java b/src/test/java/com/sonyericsson/rebuild/RebuildValidatorTest.java index 58d51db..33aaee3 100644 --- a/src/test/java/com/sonyericsson/rebuild/RebuildValidatorTest.java +++ b/src/test/java/com/sonyericsson/rebuild/RebuildValidatorTest.java @@ -50,6 +50,10 @@ import java.util.List; import java.util.concurrent.ExecutionException; +import static com.sonyericsson.rebuild.matchers.StringParameterValuesMatcher.hasStringParamValues; +import static org.hamcrest.core.IsNot.not; +import static org.junit.Assert.assertThat; + /** * For testing the extension point. * @@ -393,6 +397,110 @@ public void testRebuildSupportedUnknownParameterValue() throws Exception { page.asText().contains("This is a mark for test")); } + public void testNewParametersShouldOverrideExistingParametersIfHaveSameName() + throws Exception { + FreeStyleProject project = createFreeStyleProject(); + project.addProperty(new ParametersDefinitionProperty( + new StringParameterDefinition("existing", "defaultValue"))); + + // Build (#1) + project.scheduleBuild2(0, new Cause.UserIdCause(), + new ParametersAction(new StringParameterValue("existing", "overridingValue"))) + .get(); + HtmlPage rebuildConfigPage = createWebClient().getPage(project, + "1/rebuild"); + // Rebuild (#2) + submit(rebuildConfigPage.getFormByName("config")); + + List parameterValues = project.getBuildByNumber(2).getAction(ParametersAction.class).getParameters(); + + assertThat(parameterValues, hasStringParamValues(new StringParameterValue("existing", "overridingValue"))); + assertThat(parameterValues, not(hasStringParamValues(new StringParameterValue("existing", "defaultValue")))); + } + + public void testRebuildingLastBuildShouldMaintainExistingParameters() + throws Exception { + FreeStyleProject project = createFreeStyleProject(); + project.addProperty(new ParametersDefinitionProperty( + new StringParameterDefinition("existing", "defaultValue"))); + + // Build (#1) + project.scheduleBuild2(0, new Cause.UserIdCause(), + new ParametersAction(new StringParameterValue("existing", "overridingValue"))) + .get(); + HtmlPage rebuildConfigPage = createWebClient().getPage(project, + "1/rebuild"); + // Rebuild (#2) + submit(rebuildConfigPage.getFormByName("config")); + + HtmlPage projectPage = createWebClient().getPage(project); + WebAssert.assertLinkPresentWithText(projectPage, "Rebuild Last"); + + HtmlAnchor rebuildHref = projectPage.getAnchorByText("Rebuild Last"); + assertEquals("Rebuild Last should point to the second build", "/" + + project.getUrl() + "lastCompletedBuild/rebuild", + rebuildHref.getHrefAttribute()); + + List parameterValues = project.getLastCompletedBuild().getAction(ParametersAction.class).getParameters(); + + assertThat(parameterValues, hasStringParamValues(new StringParameterValue("existing", "overridingValue"))); + assertThat(parameterValues, not(hasStringParamValues(new StringParameterValue("existing", "defaultValue")))); + } + + public void testInjectedParametersShouldOverrideExistingParametersIfHaveSameName() + throws Exception { + FreeStyleProject project = createFreeStyleProject(); + project.addProperty(new ParametersDefinitionProperty( + new StringParameterDefinition("oldName", "oldValue"))); + + // Build (#1) + project.scheduleBuild2(0, new Cause.UserIdCause(), + new ParametersAction(new StringParameterValue("injectedName", "injectedValue"))) + .get(); + HtmlPage rebuildConfigPage = createWebClient().getPage(project, + "1/rebuild"); + // Rebuild (#2) + submit(rebuildConfigPage.getFormByName("config")); + + List parameterValues = project.getBuildByNumber(2).getAction(ParametersAction.class).getParameters(); + + assertThat(parameterValues, hasStringParamValues( + new StringParameterValue("oldName", "oldValue"), + new StringParameterValue("injectedName", "injectedValue") + )); + } + + public void testRebuildingLastBuildShouldMaintainInjectedParameters() + throws Exception { + FreeStyleProject project = createFreeStyleProject(); + project.addProperty(new ParametersDefinitionProperty( + new StringParameterDefinition("oldName", "oldValue"))); + + // Build (#1) + project.scheduleBuild2(0, new Cause.UserIdCause(), + new ParametersAction(new StringParameterValue("injectedName", "injectedValue"))) + .get(); + HtmlPage rebuildConfigPage = createWebClient().getPage(project, + "1/rebuild"); + // Rebuild (#2) + submit(rebuildConfigPage.getFormByName("config")); + + HtmlPage projectPage = createWebClient().getPage(project); + WebAssert.assertLinkPresentWithText(projectPage, "Rebuild Last"); + + HtmlAnchor rebuildHref = projectPage.getAnchorByText("Rebuild Last"); + assertEquals("Rebuild Last should point to the second build", "/" + + project.getUrl() + "lastCompletedBuild/rebuild", + rebuildHref.getHrefAttribute()); + + List parameterValues = project.getLastCompletedBuild().getAction(ParametersAction.class).getParameters(); + + assertThat(parameterValues, hasStringParamValues( + new StringParameterValue("oldName", "oldValue"), + new StringParameterValue("injectedName", "injectedValue") + )); + } + /** * A parameter value rebuild plugin does not know. */ diff --git a/src/test/java/com/sonyericsson/rebuild/matchers/StringParameterValuesMatcher.java b/src/test/java/com/sonyericsson/rebuild/matchers/StringParameterValuesMatcher.java new file mode 100644 index 0000000..2d8a05d --- /dev/null +++ b/src/test/java/com/sonyericsson/rebuild/matchers/StringParameterValuesMatcher.java @@ -0,0 +1,54 @@ +package com.sonyericsson.rebuild.matchers; + +import hudson.model.ParameterValue; +import hudson.model.StringParameterValue; +import org.hamcrest.Description; +import org.junit.internal.matchers.TypeSafeMatcher; + +import java.util.ArrayList; +import java.util.Collection; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +public final class StringParameterValuesMatcher extends TypeSafeMatcher> { + + private final List thisParameters; + + public static StringParameterValuesMatcher hasStringParamValues(StringParameterValue... parameters) { + return new StringParameterValuesMatcher(parameters); + } + + StringParameterValuesMatcher(StringParameterValue... parameters) { + this.thisParameters = new ArrayList(parameters.length); + for (StringParameterValue parameter : parameters) { + thisParameters.add(parameter); + } + } + + @Override + public boolean matchesSafely(Collection parameters) { + Map resultMap = new HashMap(); + for (StringParameterValue stringParameterValue : thisParameters) { + resultMap.put(stringParameterValue, false); + for (ParameterValue parameter : parameters) { + if (matchesInternal(stringParameterValue, parameter)) { + resultMap.put(stringParameterValue, true); + break; + } + } + } + return !resultMap.values().contains(false); + } + + private boolean matchesInternal(StringParameterValue thisParameter, ParameterValue parameter) { + return parameter instanceof StringParameterValue + && thisParameter.getName().equals((parameter).getName()) + && thisParameter.value.equals(((StringParameterValue)parameter).value); + } + + @Override + public void describeTo(Description description) { + description.appendValueList("<[", ", ", "]>", thisParameters); + } +}