Skip to content

Commit fbd6fe5

Browse files
authored
Merge pull request #262 from didiez/fix-repeated-SubversionTagAction
[JENKINS-35176] Fixes repeated same "Tag this build" links added to builds.
2 parents 622e3d5 + 955aa91 commit fbd6fe5

File tree

2 files changed

+58
-10
lines changed

2 files changed

+58
-10
lines changed

src/main/java/hudson/scm/SubversionSCM.java

+18-10
Original file line numberDiff line numberDiff line change
@@ -161,8 +161,6 @@
161161
import org.apache.tools.ant.BuildException;
162162
import org.apache.tools.ant.Project;
163163
import org.apache.tools.ant.taskdefs.Chmod;
164-
import org.kohsuke.accmod.Restricted;
165-
import org.kohsuke.accmod.restrictions.NoExternalUse;
166164
import org.kohsuke.stapler.AncestorInPath;
167165
import org.kohsuke.stapler.DataBoundConstructor;
168166
import org.kohsuke.stapler.QueryParameter;
@@ -192,10 +190,12 @@
192190
import com.trilead.ssh2.DebugLogger;
193191
import com.trilead.ssh2.SCPClient;
194192
import com.trilead.ssh2.crypto.Base64;
193+
import static java.util.stream.Collectors.toList;
195194
import javax.annotation.Nonnull;
196195
import jenkins.MasterToSlaveFileCallable;
197196
import jenkins.security.Roles;
198197
import jenkins.security.SlaveToMasterCallable;
198+
import org.apache.commons.collections.CollectionUtils;
199199
import org.jenkinsci.remoting.RoleChecker;
200200
import org.kohsuke.stapler.interceptor.RequirePOST;
201201

@@ -882,18 +882,18 @@ public boolean requiresWorkspaceForPolling() {
882882
}
883883
}
884884

885+
List<SvnInfoP> pList = workspace.act(new BuildRevisionMapTask(build, this, listener, externalsForAll, env));
886+
List<SvnInfo> revList = pList.stream().map(svnInfoP -> svnInfoP.info).collect(toList());
887+
885888
// write out the revision file
886889
try (PrintWriter w = new PrintWriter(new FileOutputStream(getRevisionFile(build)))) {
887-
List<SvnInfoP> pList = workspace.act(new BuildRevisionMapTask(build, this, listener, externalsForAll, env));
888-
List<SvnInfo> revList= new ArrayList<SvnInfo>(pList.size());
889890
for (SvnInfoP p: pList) {
890-
if (p.pinned)
891+
if (p.pinned) {
891892
w.println( p.info.url +'/'+ p.info.revision + "::p");
892-
else
893+
} else {
893894
w.println( p.info.url +'/'+ p.info.revision);
894-
revList.add(p.info);
895+
}
895896
}
896-
build.addAction(new SubversionTagAction(build,revList));
897897
}
898898

899899
// write out the externals info
@@ -903,8 +903,16 @@ public boolean requiresWorkspaceForPolling() {
903903
projectExternalsCache.put(build.getParent(), externalsForAll);
904904
}
905905

906-
if (changelogFile != null) {
907-
calcChangeLog(build, workspace, changelogFile, baseline, listener, externalsMap, env);
906+
// check if a SubversionTagAction with the same scm changes has been already added in a previous checkout/update in the build
907+
boolean scmChangesAlreadyProcessed = build.getActions(SubversionTagAction.class).stream()
908+
.anyMatch(existingTagAction -> CollectionUtils.isEqualCollection(existingTagAction.getTags().keySet(), revList));
909+
910+
// Don't add the tag and changelog if no changelog was requested or we've already processed this scm changes before
911+
if(changelogFile != null && !scmChangesAlreadyProcessed) {
912+
// add the tag action
913+
build.addAction(new SubversionTagAction(build,revList));
914+
// write out the changelog file
915+
calcChangeLog(build, workspace, changelogFile, baseline, listener, externalsMap, env);
908916
}
909917
}
910918

src/test/java/jenkins/scm/impl/subversion/SubversionStepTest.java

+40
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
import hudson.scm.ChangeLogSet;
2727
import hudson.scm.SCM;
2828
import hudson.scm.SubversionSCM;
29+
import hudson.scm.SubversionTagAction;
2930
import hudson.triggers.SCMTrigger;
3031
import java.util.Iterator;
3132
import java.util.List;
@@ -38,6 +39,7 @@
3839
import org.junit.Rule;
3940
import org.junit.Test;
4041
import org.jvnet.hudson.test.BuildWatcher;
42+
import org.jvnet.hudson.test.Issue;
4143
import org.jvnet.hudson.test.JenkinsRule;
4244

4345
public class SubversionStepTest {
@@ -116,6 +118,44 @@ public void multipleSCMs() throws Exception {
116118
assertFalse(iterator.hasNext());
117119
}
118120

121+
@Issue("JENKINS-38204")
122+
@Test
123+
public void identicalSCMs() throws Exception {
124+
sampleRepo.init();
125+
WorkflowJob p = r.jenkins.createProject(WorkflowJob.class, "demo");
126+
p.setDefinition(new CpsFlowDefinition(
127+
"node {\n" +
128+
" dir('main') {\n" +
129+
" svn(url: '" + sampleRepo.trunkUrl() + "')\n" +
130+
" }\n" +
131+
" dir('other') {\n" +
132+
" svn(url: '" + sampleRepo.trunkUrl() + "')\n" +
133+
" }\n" +
134+
"}", true));
135+
136+
WorkflowRun b = r.assertBuildStatusSuccess(p.scheduleBuild2(0));
137+
assertEquals(1, b.getActions(SubversionTagAction.class).size());
138+
assertEquals(0, b.getChangeSets().size());
139+
assertEquals(1, p.getSCMs().size());
140+
141+
// add a file and commit
142+
sampleRepo.write("otherfile", "");
143+
sampleRepo.svnkit("add", sampleRepo.wc() + "/" + "otherfile");
144+
sampleRepo.svnkit("commit", "--message=+otherfile", sampleRepo.wc());
145+
146+
WorkflowRun b2 = r.assertBuildStatusSuccess(p.scheduleBuild2(0));
147+
148+
// there should by only one tag action and changeset
149+
assertEquals(1, b2.getActions(SubversionTagAction.class).size());
150+
assertEquals(1, b2.getChangeSets().size());
151+
152+
// check items of the only changeset
153+
ChangeLogSet changeSet = b2.getChangeSets().get(0);
154+
assertFalse(changeSet.isEmptySet());
155+
assertEquals(1, changeSet.getItems().length);
156+
157+
assertEquals(1, p.getSCMs().size());
158+
}
119159

120160
@Test
121161
public void checkoutDepthAsItIsInfiniteTest() throws Exception {

0 commit comments

Comments
 (0)