Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP

Loading…

Cancel old jobs when a new patch is uploaded #5

Merged
merged 1 commit into from

6 participants

@bnovc

When a new patch set is posted, building the previous patch set
is no longer valuable. This causes an enormous extra load on the
build servers. If someone rapidly posts several revisions of a
patch, it could cause enormous delays and wasted resources in
Jenkins.

If others feel a need to make this an option, I can, but for the
environments I have seen, this is always desired behavior.

@rtyler
Collaborator

This maps to our desired use case as well.

Stupid GitHub doesn't let me just "watch" a pull request without making an inane comment :)

@rsandell
Collaborator

Great! I've been wanting this feature as well for a long time.
I will take a closer look at it as soon as I'm able.

@rsandell
Collaborator

Looks good, I actually have a user or two who would like to be able to turn this off.

Could you add a unit test or two to verify that we don't break the it in the future.

@bnovc

I made this optional, so I think this is acceptable to go in. I still get errors trying to run the unit tests. I'll email you my current ones.

@VestniK VestniK commented on the diff
...ugins/gerrit/trigger/hudsontrigger/GerritTrigger.java
@@ -249,12 +267,31 @@ protected void schedule(GerritCause cause, PatchsetCreated event, AbstractProjec
new RetriggerAllAction(cause.getContext()),
createParameters(event, project));
+ // check if we're running any jobs for this event
+ if (runningJobs.containsKey(event.getChange())) {
+ // if we were, let's cancel them
+ Future oldBuild = runningJobs.remove(event.getChange());
+ if (PluginImpl.getInstance().getConfig().isGerritBuildCurrentPatchesOnly()) {
@VestniK
VestniK added a note

Is it really necessary to remove item from runningJobs if this condition is false? Would it be better to rewrite this block in the following way:
if (runningJobs.containsKey(event.getChange()) && PluginImpl.getInstance().getConfig().isGerritBuildCurrentPatchesOnly()) {
Future oldBuild = runningJobs.remove(event.getChange());
oldBuild.cancel(true)
}
?

@bnovc
bnovc added a note

I wrote it this way so the option could be off and then turned on and work for existing jobs (see that it adds them unconditionally also).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
@VestniK VestniK commented on the diff
...ugins/gerrit/trigger/hudsontrigger/GerritTrigger.java
@@ -241,7 +259,7 @@ protected void schedule(GerritCause cause, PatchsetCreated event) {
*/
protected void schedule(GerritCause cause, PatchsetCreated event, AbstractProject project) {
//during low traffic we still don't want to spam Gerrit, 3 is a nice number, isn't it?
- boolean ok = project.scheduleBuild(
+ Future build = project.scheduleBuild2(
@VestniK
VestniK added a note

You should modify the tests which expects scheduleBuild to be called as well (there are 17 in the GerritTriggerTest class which fails now)

@bnovc
bnovc added a note

I couldn't ever get the tests to run. That's why I've left this patch dormant. I get a ton of connection errors on one machine I tried it on, and I can't even get mvn package to run on my other machine (it hangs downloading dependencies every time). Hadn't spent the time looking into either of those, yet.

Do you just run mvn package, and you get errors about this?

I'll take your change (89d1c9) and incorporate it into this.

@VestniK
VestniK added a note

Yes both "mvn package" and "mvn install" runs tests. I'm using fresh Ubuntu installation (witn open-jdk-6 and maven2 packages from officiall repository) and Arch Linux (again open-jdk-6 and maven2 from off. repos.). Everything works fine on both systems.

Tried your commit. All tests are passed.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
@VestniK

In order to pass all of the tests I had to make the following changes: VestniK@89d1c97

@VestniK

I'm unsure about my changes in the first diff (ToGerritRunListener.java file). I've tried to fix NullPointerException at com.sonyericsson.hudson.plugins.gerrit.trigger.gerritnotifier.ToGerritRunListenerTest.testOnCompleted (ToGerritRunListenerTest.java:132) Can somebody take a look on it?

I'm ready to test merge of this pull request with my open pull request (#4 and #8) in our working environment.

...ugins/gerrit/trigger/hudsontrigger/GerritTrigger.java
((18 lines not shown))
event.getChange().getNumber() + "/" + event.getPatchSet().getNumber(), });
}
/**
+ * Used to inform the plugin that the builds for a job have ended
+ * This allows us to clean up our list of what jobs we're running
+ */
+ public void notifyBuildEnded(PatchsetCreated patchset) {
+ runningJobs.remove(patchset);
@VestniK
VestniK added a note

Should this line be runningJobs.remove(patchset.getChange()); ?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Anthony Newnam Cancel jobs when a new patch set is created
When a new patch set is posted, building the previous patch set
is no longer valuable. This causes an enormous extra load on the
build servers. If someone rapidly posts several revisions of a
patch, it could cause enormous delays and wasted resources in
Jenkins.

This only does part of the work, because calling cancel() on a
Future that is provided by scheduleBuild2() does not cancel jobs
that are in the queue. A ticket has been created to address this,
available at: https://issues.jenkins-ci.org/browse/JENKINS-12152
81d484c
@bnovc

Ping

@rsandell
Collaborator

Sorry, I didn't get notified when new commits got added, and I was waiting for how the discussions around VestniK's comments turned out :)
I'll take a look soon.

@bnovc

This is causing a NPE on our Jenkins instance. I haven't had a chance/environment to debug it, yet. It seems like this may be a symptom of another problem within the plugin creating invalid patch sets, but I may be mis-using them.

INFO: JenkinsAdmin-Gerrit-trigger-verification #180 main build action completed: SUCCESS
Feb 1, 2012 6:50:49 AM hudson.model.Executor run
SEVERE: Executor threw an exception
java.lang.NullPointerException
at com.sonyericsson.hudson.plugins.gerrit.trigger.hudsontrigger.GerritTrigger.notifyBuildEnded(GerritTrigger.java:291)
at com.sonyericsson.hudson.plugins.gerrit.trigger.gerritnotifier.ToGerritRunListener.onCompleted(ToGerritRunListener.java:90)
at com.sonyericsson.hudson.plugins.gerrit.trigger.gerritnotifier.ToGerritRunListener.onCompleted(ToGerritRunListener.java:49)
at hudson.model.listeners.RunListener.fireCompleted(RunListener.java:178)
at hudson.model.Run.run(Run.java:1454)
at hudson.model.FreeStyleBuild.run(FreeStyleBuild.java:46)
at hudson.model.ResourceController.execute(ResourceController.java:88)
at hudson.model.Executor.run(Executor.java:238)

@rsandell
Collaborator

Do you think it is something caused by this change?

@bnovc

I don't know if it is caused by it; it seems like it may just be exposing a problem. It was working fine for a while, also.

@rsandell rsandell merged commit a9342a4 into jenkinsci:master
@rsandell
Collaborator

Hmm, We've done some testing on it. And we get some strange behaviour.
The test cases that I wrote pass like a charm so it seems to work.
But when we test it with a running server, both via mvn hpi:run and on a Testing server running Jenkins 1.424.1 in a tomcat instance, the build don't get cancelled.

I wrote a groovy script that fetches the runningJobs var and runs the following command on it:
println("\tCanceled: " + trigger.runningJobs.values().iterator().next().cancel(true));
So in effect it is running the same method that the code is doing. The cancel call returns true but the build keeps on building and its only a shell doing sleep 300.
Clicking cancel on the build page works.

any ideas?

@bnovc

Odd, that isn't the behavior that I have. What version of Jenkins are you running? I'm on 1.441. The master and slaves are Windows Server 2008. I think they're on a 64bit JVM.

Is the "sleep 300" in an "Execute shell" box?

@rsandell
Collaborator

Tested on 1.424.1 and when you run with maven it is 1.400 since that is what the pom is configured for.
Ubuntu 10.04 64bit.

Yes the sleep is in an execute shell box, but cancelling the build from the UI works, so it's not like the build isn't possible to kill, its just future.cancel that doesn't aparently.

@TWestling
Collaborator

Now we have tested on 1.441 on Windows XP to rule out all differences.
What we see on both linux/windows and 1.400/1.424/1.441 is the same:

Submitting two patch sets on the same change works fine, the first one is cancelled.
Adding the third patch set doesn't cause the nr 2 to cancel. Any further patch sets added
while nr 3 is waiting on nr 2 won't trigger at all.

Manually cancelling nr 2 and nr 3 can get it working
again ( for the duration of one new patch set, then it bugs out again ) but it can also end up in a state where nothing is triggered, even though no builds are in queue or building.

We also noticed a nullpointer being thrown when an old project is deserialized from a server restart, this was what caused what Bobby described above, when we couldn't get it to work at all. We have a fix for the Nullpointer, but after quite a bit of debugging, we still can't explain the weird behavior I described above.

bnovc, could you test adding a lot of patch sets after each other to the same change and see if you can reproduce this problem?

@bnovc

I was able to reproduce this. The problem looks like it is because we're doing .remove() on the generic change, but it needs to be sure to only remove the change if it is also the same patch set. I'll put up a patch for this soon (maybe Monday as I'm heading home).

I also experienced a weird problem after pulling in the changes that went on top of this. runningJobs was always null for me. It seems that the explicit constructor that should have created it was not being created. I changed it to a singleton function to create and return it which avoided the problem. Seems kind of like a Java bug, but I haven't looked anymore into that.

@rsandell
Collaborator

I fixed the null problem with commit 8d976b4
I also added some thread safety in that as well.

@bnovc

Sorry I wasn't clear. I meant a different NPE problem. I've posted a fix to my NPE problem and the canceling issue. See #11

@brianjmurrell

Is this feature stable yet?

@rsandell
Collaborator

Yes as of version 2.7.0 we consider it stable.
From the changelog:
"Build current patchsets only is no longer experimental"

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Commits on Jan 5, 2012
  1. Cancel jobs when a new patch set is created

    Anthony Newnam authored
    When a new patch set is posted, building the previous patch set
    is no longer valuable. This causes an enormous extra load on the
    build servers. If someone rapidly posts several revisions of a
    patch, it could cause enormous delays and wasted resources in
    Jenkins.
    
    This only does part of the work, because calling cancel() on a
    Future that is provided by scheduleBuild2() does not cancel jobs
    that are in the queue. A ticket has been created to address this,
    available at: https://issues.jenkins-ci.org/browse/JENKINS-12152
This page is out of date. Refresh to see the latest.
View
20 gerrithudsontrigger/src/main/java/com/sonyericsson/hudson/plugins/gerrit/trigger/config/Config.java
@@ -74,11 +74,13 @@
* Default verified vote to Gerrit when a build is successful.
*/
public static final boolean DEFAULT_ENABLE_MANUAL_TRIGGER = true;
+ public static final boolean DEFAULT_BUILD_CURRENT_PATCHES_ONLY = true;
private String gerritHostName;
private int gerritSshPort;
private String gerritUserName;
private File gerritAuthKeyFile;
private String gerritAuthKeyFilePassword;
+ private boolean gerritBuildCurrentPatchesOnly;
private int numberOfWorkerThreads;
private String gerritVerifiedCmdBuildSuccessful;
private String gerritVerifiedCmdBuildUnstable;
@@ -124,6 +126,9 @@ public void setValues(JSONObject formData) {
if (gerritAuthKeyFilePassword != null && gerritAuthKeyFilePassword.length() <= 0) {
gerritAuthKeyFilePassword = null;
}
+ gerritBuildCurrentPatchesOnly = formData.optBoolean(
+ "gerritBuildCurrentPatchesOnly",
+ DEFAULT_BUILD_CURRENT_PATCHES_ONLY);
numberOfWorkerThreads = formData.optInt(
"numberOfReceivingWorkerThreads",
@@ -240,6 +245,16 @@ public void setGerritAuthKeyFilePassword(String gerritAuthKeyFilePassword) {
this.gerritAuthKeyFilePassword = gerritAuthKeyFilePassword;
}
+ /**
+ * GerritBuildCurrentPatchesOnly
+ *
+ * @param gerritBuildCurrentPatchesOnly whether to only build the current patch set
+ * @see #isGerritBuildCurrentPatchesOnly()
+ */
+ public void setGerritBuildCurrentPatchesOnly(boolean gerritBuildCurrentPatchesOnly) {
+ this.gerritBuildCurrentPatchesOnly = gerritBuildCurrentPatchesOnly;
+ }
+
@Override
public String getGerritFrontEndUrl() {
String url = gerritFrontEndUrl;
@@ -346,6 +361,11 @@ public void setNumberOfReceivingWorkerThreads(int numberOfReceivingWorkerThreads
}
@Override
+ public boolean isGerritBuildCurrentPatchesOnly() {
+ return gerritBuildCurrentPatchesOnly;
+ }
+
+ @Override
public String getGerritCmdBuildSuccessful() {
return gerritVerifiedCmdBuildSuccessful;
}
View
6 ...gger/src/main/java/com/sonyericsson/hudson/plugins/gerrit/trigger/config/IGerritHudsonTriggerConfig.java
@@ -33,6 +33,12 @@
public interface IGerritHudsonTriggerConfig extends GerritConnectionConfig {
/**
+ * If enabled, then old patch revision builds will be canceled
+ * @return true if so.
+ */
+ boolean isGerritBuildCurrentPatchesOnly();
+
+ /**
* Base URL for the Gerrit UI.
* @return the gerrit front end URL. Always ends with '/'
*/
View
21 ...igger/src/main/java/com/sonyericsson/hudson/plugins/gerrit/trigger/gerritnotifier/ParameterExpander.java
@@ -89,7 +89,7 @@ public ParameterExpander(IGerritHudsonTriggerConfig config) {
public String getBuildStartedCommand(AbstractBuild r, TaskListener taskListener,
PatchsetCreated event, BuildsStartedStats stats) {
- GerritTrigger trigger = getTrigger(r.getProject());
+ GerritTrigger trigger = GerritTrigger.getTrigger(r.getProject());
String gerritCmd = config.getGerritCmdBuildStarted();
Map<String, String> parameters = createStandardParameters(r, event,
getBuildStartedCodeReviewValue(r),
@@ -115,7 +115,7 @@ public String getBuildStartedCommand(AbstractBuild r, TaskListener taskListener,
* @return the value.
*/
private int getBuildStartedVerifiedValue(AbstractBuild r) {
- GerritTrigger trigger = getTrigger(r.getProject());
+ GerritTrigger trigger = GerritTrigger.getTrigger(r.getProject());
if (trigger == null) {
logger.warn("Unable to get trigger config for build {} will use global value.");
return config.getGerritBuildStartedVerifiedValue();
@@ -139,7 +139,7 @@ private int getBuildStartedVerifiedValue(AbstractBuild r) {
* @return the value.
*/
private int getBuildStartedCodeReviewValue(AbstractBuild r) {
- GerritTrigger trigger = getTrigger(r.getProject());
+ GerritTrigger trigger = GerritTrigger.getTrigger(r.getProject());
if (trigger == null) {
logger.warn("Unable to get trigger config for build {} will use global value.");
return config.getGerritBuildStartedCodeReviewValue();
@@ -195,15 +195,6 @@ private int getBuildStartedCodeReviewValue(AbstractBuild r) {
}
/**
- * Finds the GerritTrigger in a project.
- * @param project the project.
- * @return the trigger if there is one, null otherwise.
- */
- private GerritTrigger getTrigger(AbstractProject project) {
- return (GerritTrigger)project.getTrigger(GerritTrigger.class);
- }
-
- /**
* Expands all types of parameters in the string and returns the "replaced" string.
* Both types means both $ENV_VARS and &lt;PLUGIN_VARS&gt;
* @param gerritCommand the command "template"
@@ -311,7 +302,7 @@ protected int getMinimumVerifiedValue(MemoryImprint memoryImprint) {
for (Entry entry : memoryImprint.getEntries()) {
verified = Math.min(verified, getVerifiedValue(
entry.getBuild().getResult(),
- getTrigger(entry.getProject())));
+ GerritTrigger.getTrigger(entry.getProject())));
}
return verified;
}
@@ -326,7 +317,7 @@ protected int getMinimumCodeReviewValue(MemoryImprint memoryImprint) {
for (Entry entry : memoryImprint.getEntries()) {
codeReview = Math.min(codeReview, getCodeReviewValue(
entry.getBuild().getResult(),
- getTrigger(entry.getProject())));
+ GerritTrigger.getTrigger(entry.getProject())));
}
return codeReview;
}
@@ -386,7 +377,7 @@ private String createBuildsStats(MemoryImprint memoryImprint) {
for (Entry entry : entries) {
AbstractBuild build = entry.getBuild();
if (build != null) {
- GerritTrigger trigger = getTrigger(build.getProject());
+ GerritTrigger trigger = GerritTrigger.getTrigger(build.getProject());
Result res = build.getResult();
String customMessage = null;
View
5 ...ger/src/main/java/com/sonyericsson/hudson/plugins/gerrit/trigger/gerritnotifier/ToGerritRunListener.java
@@ -28,6 +28,7 @@
import com.sonyericsson.hudson.plugins.gerrit.trigger.gerritnotifier.model.BuildMemory.PatchSetKey;
import com.sonyericsson.hudson.plugins.gerrit.trigger.gerritnotifier.model.BuildsStartedStats;
import com.sonyericsson.hudson.plugins.gerrit.trigger.hudsontrigger.GerritCause;
+import com.sonyericsson.hudson.plugins.gerrit.trigger.hudsontrigger.GerritTrigger;
import hudson.Extension;
import hudson.model.AbstractBuild;
import hudson.model.AbstractProject;
@@ -84,6 +85,10 @@ public synchronized void onCompleted(AbstractBuild r, TaskListener listener) {
if (cause != null) {
cleanUpGerritCauses(cause, r);
PatchsetCreated event = cause.getEvent();
+ if (GerritTrigger.getTrigger(r.getProject()) != null) {
+ // There won't be a trigger if this job was run through a unit test
+ GerritTrigger.getTrigger(r.getProject()).notifyBuildEnded(event);
+ }
event.fireBuildCompleted(r);
if (!cause.isSilentMode()) {
PatchSetKey key = memory.completed(event, r);
View
3  ...igger/src/main/java/com/sonyericsson/hudson/plugins/gerrit/trigger/gerritnotifier/model/BuildMemory.java
@@ -178,8 +178,9 @@ public synchronized PatchSetKey started(PatchsetCreated event, AbstractBuild bui
PatchSetKey key = createKey(event);
MemoryImprint pb = memory.get(key);
if (pb == null) {
- //Shoudn't happen but just in case, keep the memory.
+ //A build should not start for a job that hasn't been registered. Keep the memory anyway.
pb = new MemoryImprint(event);
+ logger.warn("Build started without being registered first.");
memory.put(key, pb);
}
pb.set(build.getProject(), build);
View
41 ...sontrigger/src/main/java/com/sonyericsson/hudson/plugins/gerrit/trigger/hudsontrigger/GerritTrigger.java
@@ -23,6 +23,8 @@
*/
package com.sonyericsson.hudson.plugins.gerrit.trigger.hudsontrigger;
+import static com.sonyericsson.hudson.plugins.gerrit.gerritevents.GerritDefaultValues.DEFAULT_BUILD_SCHEDULE_DELAY;
+import com.sonyericsson.hudson.plugins.gerrit.gerritevents.dto.attr.Change;
import com.sonyericsson.hudson.plugins.gerrit.gerritevents.GerritEventListener;
import com.sonyericsson.hudson.plugins.gerrit.gerritevents.dto.GerritEvent;
import com.sonyericsson.hudson.plugins.gerrit.gerritevents.dto.events.ChangeAbandoned;
@@ -54,6 +56,9 @@
import java.util.ArrayList;
import java.util.List;
+import org.kohsuke.stapler.QueryParameter;
+import java.util.HashMap;
+import java.util.concurrent.Future;
import static com.sonyericsson.hudson.plugins.gerrit.gerritevents.GerritDefaultValues.DEFAULT_BUILD_SCHEDULE_DELAY;
import static com.sonyericsson.hudson.plugins.gerrit.trigger.hudsontrigger.GerritTriggerParameters.setOrCreateParameters;
@@ -71,6 +76,8 @@
private static final int HASH_NUMBER = 53;
private static final Logger logger = LoggerFactory.getLogger(GerritTrigger.class);
+ //! Association between patches and the jobs that we're running for them
+ private transient HashMap<Change, Future> runningJobs = new HashMap<Change, Future>();
private transient AbstractProject myProject;
private List<GerritProject> gerritProjects;
private Integer gerritBuildStartedVerifiedValue;
@@ -157,6 +164,15 @@ public GerritTrigger(
this.buildFailureMessage = buildFailureMessage;
}
+ /**
+ * Finds the GerritTrigger in a project.
+ * @param project the project.
+ * @return the trigger if there is one, null otherwise.
+ */
+ public static GerritTrigger getTrigger(AbstractProject project) {
+ return (GerritTrigger)project.getTrigger(GerritTrigger.class);
+ }
+
@Override
public void start(AbstractProject project, boolean newInstance) {
logger.debug("Start project: {}", project);
@@ -204,6 +220,7 @@ public void gerritEvent(PatchsetCreated event) {
logger.trace("Disabled.");
return;
}
+
if (isInteresting(event)) {
logger.trace("The event is interesting.");
if (!silentMode) {
@@ -217,6 +234,7 @@ public void gerritEvent(PatchsetCreated event) {
} else {
cause = new GerritCause(event, silentMode);
}
+
schedule(cause, event);
}
}
@@ -241,7 +259,7 @@ protected void schedule(GerritCause cause, PatchsetCreated event) {
*/
protected void schedule(GerritCause cause, PatchsetCreated event, AbstractProject project) {
//during low traffic we still don't want to spam Gerrit, 3 is a nice number, isn't it?
- boolean ok = project.scheduleBuild(
+ Future build = project.scheduleBuild2(
@VestniK
VestniK added a note

You should modify the tests which expects scheduleBuild to be called as well (there are 17 in the GerritTriggerTest class which fails now)

@bnovc
bnovc added a note

I couldn't ever get the tests to run. That's why I've left this patch dormant. I get a ton of connection errors on one machine I tried it on, and I can't even get mvn package to run on my other machine (it hangs downloading dependencies every time). Hadn't spent the time looking into either of those, yet.

Do you just run mvn package, and you get errors about this?

I'll take your change (89d1c9) and incorporate it into this.

@VestniK
VestniK added a note

Yes both "mvn package" and "mvn install" runs tests. I'm using fresh Ubuntu installation (witn open-jdk-6 and maven2 packages from officiall repository) and Arch Linux (again open-jdk-6 and maven2 from off. repos.). Everything works fine on both systems.

Tried your commit. All tests are passed.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
getBuildScheduleDelay(),
cause,
new BadgeAction(event),
@@ -249,12 +267,31 @@ protected void schedule(GerritCause cause, PatchsetCreated event, AbstractProjec
new RetriggerAllAction(cause.getContext()),
createParameters(event, project));
+ // check if we're running any jobs for this event
+ if (runningJobs.containsKey(event.getChange())) {
+ // if we were, let's cancel them
+ Future oldBuild = runningJobs.remove(event.getChange());
+ if (PluginImpl.getInstance().getConfig().isGerritBuildCurrentPatchesOnly()) {
@VestniK
VestniK added a note

Is it really necessary to remove item from runningJobs if this condition is false? Would it be better to rewrite this block in the following way:
if (runningJobs.containsKey(event.getChange()) && PluginImpl.getInstance().getConfig().isGerritBuildCurrentPatchesOnly()) {
Future oldBuild = runningJobs.remove(event.getChange());
oldBuild.cancel(true)
}
?

@bnovc
bnovc added a note

I wrote it this way so the option could be off and then turned on and work for existing jobs (see that it adds them unconditionally also).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
+ oldBuild.cancel(true);
+ }
+ }
+ // add our new job
+ runningJobs.put(event.getChange(), build);
+
logger.info("Project {} Build Scheduled: {} By event: {}",
- new Object[]{project.getName(), ok,
+ new Object[]{project.getName(), (build != null),
event.getChange().getNumber() + "/" + event.getPatchSet().getNumber(), });
}
/**
+ * Used to inform the plugin that the builds for a job have ended
+ * This allows us to clean up our list of what jobs we're running
+ */
+ public void notifyBuildEnded(PatchsetCreated patchset) {
+ runningJobs.remove(patchset.getChange());
+ }
+
+ /**
* getBuildScheduleDelay method will return configured
* buildScheduledelay value.
* If the value is missing or invalid it the method
View
6 ...ontrigger/src/main/resources/com/sonyericsson/hudson/plugins/gerrit/trigger/GerritManagement/index.jelly
@@ -50,6 +50,12 @@
value="${it.config.gerritAuthKeyFilePassword}"
default="${com.sonyericsson.hudson.plugins.gerrit.gerritevents.GerritDefaultValues.DEFAULT_GERRIT_AUTH_KEY_FILE_PASSWORD}"/>
</f:entry>
+ <f:entry title="${%Build Current Patches Only}"
+ help="/plugin/gerrit-trigger/help-GerritBuildCurrentPatchesOnly.html">
+ <f:checkbox name="gerritBuildCurrentPatchesOnly"
+ checked="${it.config.gerritBuildCurrentPatchesOnly}"
+ default="true" />
+ </f:entry>
<f:validateButton title="${%Test Connection}"
progress="${%Testing...}"
method="testConnection"
View
60 ...rigger/src/test/java/com/sonyericsson/hudson/plugins/gerrit/trigger/hudsontrigger/GerritTriggerTest.java
@@ -147,7 +147,7 @@ public void testMakeRefSpec4() {
/**
* Tests the schedule method of GerritTrigger.
- * It verifies that {@link AbstractProject#scheduleBuild(int, hudson.model.Cause, hudson.model.Action...)}
+ * It verifies that {@link AbstractProject#scheduleBuild2(int, hudson.model.Cause, hudson.model.Action...)}
* gets called with an average buildScheduleDelay 20.
*/
@Test
@@ -169,7 +169,7 @@ public void testScheduleWithAverageBuildScheduleDelay() {
gerritCause = spy(gerritCause);
doReturn("http://mock.url").when(gerritCause).getUrl();
trigger.schedule(gerritCause, event);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
eq(20),
same(gerritCause),
isA(Action.class),
@@ -180,7 +180,7 @@ public void testScheduleWithAverageBuildScheduleDelay() {
/**
* Tests the schedule method of GerritTrigger.
- * It verifies that {@link AbstractProject#scheduleBuild(int, hudson.model.Cause, hudson.model.Action...)}
+ * It verifies that {@link AbstractProject#scheduleBuild2(int, hudson.model.Cause, hudson.model.Action...)}
* gets called with an negative buildScheduleDelay -20.
*/
@Test
@@ -202,7 +202,7 @@ public void testScheduleWithNegativeBuildScheduleDelay() {
gerritCause = spy(gerritCause);
doReturn("http://mock.url").when(gerritCause).getUrl();
trigger.schedule(gerritCause, event);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
//negative value will be reset into default value 3
eq(3),
same(gerritCause),
@@ -214,7 +214,7 @@ public void testScheduleWithNegativeBuildScheduleDelay() {
/**
* Tests the schedule method of GerritTrigger.
- * It verifies that {@link AbstractProject#scheduleBuild(int, hudson.model.Cause, hudson.model.Action...)}
+ * It verifies that {@link AbstractProject#scheduleBuild2(int, hudson.model.Cause, hudson.model.Action...)}
* gets called with an negative buildScheduleDelay 10000.
*/
@Test
@@ -236,7 +236,7 @@ public void testScheduleWithMaximumBuildScheduleDelay() {
gerritCause = spy(gerritCause);
doReturn("http://mock.url").when(gerritCause).getUrl();
trigger.schedule(gerritCause, event);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
eq(10000),
same(gerritCause),
isA(Action.class),
@@ -248,7 +248,7 @@ public void testScheduleWithMaximumBuildScheduleDelay() {
/**
* Tests the schedule method of GerritTrigger.
* It verifies that
- * {@link hudson.model.AbstractProject#scheduleBuild(int, hudson.model.Cause, hudson.model.Action...)}
+ * {@link hudson.model.AbstractProject#scheduleBuild2(int, hudson.model.Cause, hudson.model.Action...)}
* gets called with correct parameters when there are some default parameters present.
*/
@Test
@@ -277,7 +277,7 @@ public void testScheduleWithDefaultParameters() {
PowerMockito.when(PluginImpl.getInstance()).thenReturn(plugin);
trigger.schedule(gerritCause, event);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
same(gerritCause),
isA(Action.class),
@@ -285,7 +285,7 @@ public void testScheduleWithDefaultParameters() {
isA(Action.class),
isParameterActionWithStringParameterValue("MOCK_PARAM", "mock_value"));
//Just to make sure the normal arguments are there as well.
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
same(gerritCause),
isA(Action.class),
@@ -296,7 +296,7 @@ public void testScheduleWithDefaultParameters() {
/**
* Tests the schedule method of GerritTrigger.
- * It verifies that {@link AbstractProject#scheduleBuild(int, hudson.model.Cause, hudson.model.Action...)}
+ * It verifies that {@link AbstractProject#scheduleBuild2(int, hudson.model.Cause, hudson.model.Action...)}
* gets called with correct parameters when there are no default parameters present.
*/
@Test
@@ -323,7 +323,7 @@ public void testScheduleWithNoDefaultParameters() {
trigger.schedule(gerritCause, event);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
same(gerritCause),
isA(Action.class),
@@ -331,7 +331,7 @@ public void testScheduleWithNoDefaultParameters() {
isA(Action.class),
isParameterActionWithStringParameterValue(GERRIT_CHANGE_ID.name(), event.getChange().getId()));
//Just to make sure one more normal arguments is there as well.
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
same(gerritCause),
isA(Action.class),
@@ -342,7 +342,7 @@ public void testScheduleWithNoDefaultParameters() {
/**
* Tests the schedule method of GerritTrigger.
- * It verifies that {@link AbstractProject#scheduleBuild(int, hudson.model.Cause, hudson.model.Action...)}
+ * It verifies that {@link AbstractProject#scheduleBuild2(int, hudson.model.Cause, hudson.model.Action...)}
* gets called with correct change owner and uploader parameters when there are no default parameters present.
*/
@Test
@@ -375,7 +375,7 @@ public void testScheduleWithOwnerAndUploader() {
trigger.schedule(gerritCause, event);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
same(gerritCause),
isA(Action.class),
@@ -392,7 +392,7 @@ public void testScheduleWithOwnerAndUploader() {
/**
* Tests the schedule method of GerritTrigger.
- * It verifies that {@link AbstractProject#scheduleBuild(int, hudson.model.Cause, hudson.model.Action...)}
+ * It verifies that {@link AbstractProject#scheduleBuild2(int, hudson.model.Cause, hudson.model.Action...)}
* gets called with correct change owner and uploader parameters when there are no default parameters present.
* And sets the event.uploader to null keeping event.patchSet.uploader.
*/
@@ -426,7 +426,7 @@ public void testScheduleWithOwnerAndOneUploaderNull() {
trigger.schedule(gerritCause, event);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
same(gerritCause),
isA(Action.class),
@@ -443,7 +443,7 @@ public void testScheduleWithOwnerAndOneUploaderNull() {
/**
* Tests the schedule method of GerritTrigger.
- * It verifies that {@link AbstractProject#scheduleBuild(int, hudson.model.Cause, hudson.model.Action...)}
+ * It verifies that {@link AbstractProject#scheduleBuild2(int, hudson.model.Cause, hudson.model.Action...)}
* gets called with correct change owner and uploader parameters when there are no default parameters present.
* And sets the event.patchSet.uploader to null keeping event.uploader set.
*/
@@ -477,7 +477,7 @@ public void testScheduleWithOwnerAndOtherUploaderNull() {
trigger.schedule(gerritCause, event);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
same(gerritCause),
isA(Action.class),
@@ -494,7 +494,7 @@ public void testScheduleWithOwnerAndOtherUploaderNull() {
/**
* Tests the schedule method of GerritTrigger.
- * It verifies that {@link AbstractProject#scheduleBuild(int, hudson.model.Cause, hudson.model.Action...)}
+ * It verifies that {@link AbstractProject#scheduleBuild2(int, hudson.model.Cause, hudson.model.Action...)}
* gets called with correct change owner and uploader parameters when there are no default parameters present.
* And sets the event.patchSet.uploader and event.uploader to null.
*/
@@ -527,7 +527,7 @@ public void testScheduleWithOwnerAndBothUploadersNull() {
trigger.schedule(gerritCause, event);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
same(gerritCause),
isA(Action.class),
@@ -544,7 +544,7 @@ public void testScheduleWithOwnerAndBothUploadersNull() {
/**
* Tests the schedule method of GerritTrigger.
- * It verifies that {@link AbstractProject#scheduleBuild(int, hudson.model.Cause, hudson.model.Action...)}
+ * It verifies that {@link AbstractProject#scheduleBuild2(int, hudson.model.Cause, hudson.model.Action...)}
* gets called with correct change owner and uploader parameters when there are no default parameters present.
* And sets the event.patchSet.uploader and event.uploader to null.
*/
@@ -578,7 +578,7 @@ public void testScheduleWithOwnerAndPartOfUploadersNull() {
trigger.schedule(gerritCause, event);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
same(gerritCause),
isA(Action.class),
@@ -624,7 +624,7 @@ public void testRetriggerThisBuild() {
verify(listener).onRetriggered(same(project), same(event), anyListOf(AbstractBuild.class));
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
isA(GerritUserCause.class),
isA(BadgeAction.class),
@@ -666,7 +666,7 @@ public void testRetriggerThisBuildSilent() {
isA(PatchsetCreated.class),
anyListOf(AbstractBuild.class));
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
isA(GerritUserCause.class),
isA(BadgeAction.class),
@@ -721,7 +721,7 @@ public void testRetriggerAllBuilds() {
verify(listener).onRetriggered(thisProject, event, null);
- verify(thisProject).scheduleBuild(
+ verify(thisProject).scheduleBuild2(
anyInt(),
isA(GerritUserCause.class),
isA(BadgeAction.class),
@@ -731,7 +731,7 @@ public void testRetriggerAllBuilds() {
verify(listener).onRetriggered(otherProject, event, null);
- verify(otherProject).scheduleBuild(
+ verify(otherProject).scheduleBuild2(
anyInt(),
isA(GerritUserCause.class),
isA(BadgeAction.class),
@@ -766,7 +766,7 @@ public void testGerritEvent() {
verify(listener).onTriggered(same(project), same(event));
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
isA(GerritCause.class),
isA(BadgeAction.class),
@@ -857,7 +857,7 @@ public void testGerritEventManualEvent() {
verify(listener).onTriggered(same(project), same(event));
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
isA(GerritManualCause.class),
isA(BadgeAction.class),
@@ -892,7 +892,7 @@ public void testGerritEventSilentMode() {
verifyNoMoreInteractions(listener);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
isA(GerritCause.class),
isA(BadgeAction.class),
@@ -928,7 +928,7 @@ public void testGerritEventManualEventSilentMode() {
verifyNoMoreInteractions(listener);
- verify(project).scheduleBuild(
+ verify(project).scheduleBuild2(
anyInt(),
isA(GerritManualCause.class),
isA(BadgeAction.class),
View
4 ...ger/src/test/java/com/sonyericsson/hudson/plugins/gerrit/trigger/mock/MockGerritHudsonTriggerConfig.java
@@ -191,4 +191,8 @@ public int getBuildScheduleDelay() {
public boolean hasDefaultValues() {
return false;
}
+
+ public boolean isGerritBuildCurrentPatchesOnly() {
+ return true;
+ }
}
Something went wrong with that request. Please try again.