From b63343f66f401aca7e3b178c691d4077b75f528b Mon Sep 17 00:00:00 2001 From: steven-terrana Date: Thu, 17 Oct 2019 13:11:50 -0400 Subject: [PATCH 001/101] Update GitSCMFileSystem.java --- .../jenkins/plugins/git/GitSCMFileSystem.java | 21 ++++++++++++++----- 1 file changed, 16 insertions(+), 5 deletions(-) diff --git a/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java b/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java index eadfd7bb75..ec9a2bc2b7 100644 --- a/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java +++ b/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java @@ -254,9 +254,14 @@ public boolean supports(SCM source) { return source instanceof GitSCM && ((GitSCM) source).getUserRemoteConfigs().size() == 1 && ((GitSCM) source).getBranches().size() == 1 - && ((GitSCM) source).getBranches().get(0).getName().matches( - "^((\\Q" + Constants.R_HEADS + "\\E.*)|([^/]+)|(\\*/[^/*]+(/[^/*]+)*))$" - ); + && ( + ((GitSCM) source).getBranches().get(0).getName().matches( + "^((\\Q" + Constants.R_HEADS + "\\E.*)|([^/]+)|(\\*/[^/*]+(/[^/*]+)*))$" + ) + || ((GitSCM) source).getBranches().get(0).getName().matches( + "^((\\Q" + Constants.R_TAGS + "\\E.*)|([^/]+)|(\\*/[^/*]+(/[^/*]+)*))$" + ) + ); // we only support where the branch spec is obvious } @@ -319,11 +324,17 @@ public SCMFileSystem build(@NonNull Item owner, @NonNull SCM scm, @CheckForNull } catch (URISyntaxException ex) { listener.getLogger().println("URI syntax exception for '" + remoteName + "' " + ex); } + String prefix = Constants.R_HEADS; + if(branchSpec.getName().startsWith(Constants.R_TAGS)){ + prefix = Constants.R_TAGS; + } String headName; if (rev != null) { headName = rev.getHead().getName(); } else { - if (branchSpec.getName().startsWith(Constants.R_HEADS)) { + if (branchSpec.getName().startsWith(Constants.R_TAGS)){ + headName = branchSpec.getName().substring(Constants.R_TAGS.length()); + } else if (branchSpec.getName().startsWith(Constants.R_HEADS)) { headName = branchSpec.getName().substring(Constants.R_HEADS.length()); } else if (branchSpec.getName().startsWith("*/")) { headName = branchSpec.getName().substring(2); @@ -333,7 +344,7 @@ public SCMFileSystem build(@NonNull Item owner, @NonNull SCM scm, @CheckForNull } client.fetch_().prune().from(remoteURI, Arrays .asList(new RefSpec( - "+" + Constants.R_HEADS + headName + ":" + Constants.R_REMOTES + remoteName + "/" + "+" + prefix + headName + ":" + Constants.R_REMOTES + remoteName + "/" + headName))).execute(); listener.getLogger().println("Done."); return new GitSCMFileSystem(client, remote, Constants.R_REMOTES + remoteName + "/" +headName, (AbstractGitSCMSource.SCMRevisionImpl) rev); From 8fb7b63a3ff227050074ac46f9eaa5b6d6ae3bbb Mon Sep 17 00:00:00 2001 From: steven-terrana Date: Thu, 17 Oct 2019 13:11:50 -0400 Subject: [PATCH 002/101] JENKINS-59828: allow GitSCMFileSystem to support git tags --- .../jenkins/plugins/git/GitSCMFileSystem.java | 21 ++++++++++++++----- 1 file changed, 16 insertions(+), 5 deletions(-) diff --git a/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java b/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java index eadfd7bb75..ec9a2bc2b7 100644 --- a/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java +++ b/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java @@ -254,9 +254,14 @@ public boolean supports(SCM source) { return source instanceof GitSCM && ((GitSCM) source).getUserRemoteConfigs().size() == 1 && ((GitSCM) source).getBranches().size() == 1 - && ((GitSCM) source).getBranches().get(0).getName().matches( - "^((\\Q" + Constants.R_HEADS + "\\E.*)|([^/]+)|(\\*/[^/*]+(/[^/*]+)*))$" - ); + && ( + ((GitSCM) source).getBranches().get(0).getName().matches( + "^((\\Q" + Constants.R_HEADS + "\\E.*)|([^/]+)|(\\*/[^/*]+(/[^/*]+)*))$" + ) + || ((GitSCM) source).getBranches().get(0).getName().matches( + "^((\\Q" + Constants.R_TAGS + "\\E.*)|([^/]+)|(\\*/[^/*]+(/[^/*]+)*))$" + ) + ); // we only support where the branch spec is obvious } @@ -319,11 +324,17 @@ public SCMFileSystem build(@NonNull Item owner, @NonNull SCM scm, @CheckForNull } catch (URISyntaxException ex) { listener.getLogger().println("URI syntax exception for '" + remoteName + "' " + ex); } + String prefix = Constants.R_HEADS; + if(branchSpec.getName().startsWith(Constants.R_TAGS)){ + prefix = Constants.R_TAGS; + } String headName; if (rev != null) { headName = rev.getHead().getName(); } else { - if (branchSpec.getName().startsWith(Constants.R_HEADS)) { + if (branchSpec.getName().startsWith(Constants.R_TAGS)){ + headName = branchSpec.getName().substring(Constants.R_TAGS.length()); + } else if (branchSpec.getName().startsWith(Constants.R_HEADS)) { headName = branchSpec.getName().substring(Constants.R_HEADS.length()); } else if (branchSpec.getName().startsWith("*/")) { headName = branchSpec.getName().substring(2); @@ -333,7 +344,7 @@ public SCMFileSystem build(@NonNull Item owner, @NonNull SCM scm, @CheckForNull } client.fetch_().prune().from(remoteURI, Arrays .asList(new RefSpec( - "+" + Constants.R_HEADS + headName + ":" + Constants.R_REMOTES + remoteName + "/" + "+" + prefix + headName + ":" + Constants.R_REMOTES + remoteName + "/" + headName))).execute(); listener.getLogger().println("Done."); return new GitSCMFileSystem(client, remote, Constants.R_REMOTES + remoteName + "/" +headName, (AbstractGitSCMSource.SCMRevisionImpl) rev); From f3c65cb72548d3ab8ed863d5817624119b199455 Mon Sep 17 00:00:00 2001 From: Tim Jacomb Date: Thu, 16 Jan 2020 21:48:06 +0000 Subject: [PATCH 003/101] Upgrade to use jcasc test harness --- pom.xml | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/pom.xml b/pom.xml index af930f1f09..3771707ab3 100644 --- a/pom.xml +++ b/pom.xml @@ -33,6 +33,7 @@ true 1 false + 1.35 @@ -227,12 +228,13 @@ io.jenkins configuration-as-code + ${configuration-as-code.version} true - io.jenkins - configuration-as-code - tests + io.jenkins.configuration-as-code + test-harness + ${configuration-as-code.version} test From 5f4d7b0b79ae57157bb0e33de44d7a2616780346 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 16 Jan 2020 15:33:55 -0700 Subject: [PATCH 004/101] Add gitter chat badge to docs --- README.adoc | 1 + 1 file changed, 1 insertion(+) diff --git a/README.adoc b/README.adoc index 29037ee66f..70fc13e559 100644 --- a/README.adoc +++ b/README.adoc @@ -7,6 +7,7 @@ link:https://ci.jenkins.io/job/Plugins/job/git-plugin/job/master/[image:https:// link:https://github.com/jenkinsci/git-plugin/graphs/contributors[image:https://img.shields.io/github/contributors/jenkinsci/git-plugin.svg?color=blue[Contributors]] link:https://plugins.jenkins.io/git[image:https://img.shields.io/jenkins/plugin/i/git.svg?color=blue&label=installations[Jenkins Plugin Installs]] link:https://github.com/jenkinsci/git-plugin/releases/latest[image:https://img.shields.io/github/release/jenkinsci/git-plugin.svg?label=changelog[GitHub release]] +link:https://gitter.im/jenkinsci/git-plugin[image:https://badges.gitter.im/jenkinsci/git-plugin.svg[Gitter]] [[introduction]] == Introduction From 4d32d208630447f1079997c9522d640c7aa41f0d Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 16 Jan 2020 17:43:00 -0700 Subject: [PATCH 005/101] Fix InjectedTest hang from JTH 2.57 Use JTH 2.60 instead of 2.57 to resolve test failures and test hangs on multi-core machines. * See [JENKINS-60574](https://issues.jenkins-ci.org/browse/JENKINS-60754) * See [JENKINS-60694](https://issues.jenkins-ci.org/browse/JENKINS-60694) Exclude commons-lang3 from workflow-cps-global-lib test dependency because a newer version is provided by the jenkins test harness htmlunit implementation. --- pom.xml | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 3771707ab3..b1ed97d639 100644 --- a/pom.xml +++ b/pom.xml @@ -34,7 +34,10 @@ 1 false 1.35 - + + + 2.60 + @@ -205,6 +208,12 @@ org.jenkins-ci.plugins.workflow workflow-cps-global-lib test + + + org.apache.commons + commons-lang3 + + org.xmlunit From 61e831714df2acdc4be771b9eb69e127606a3b1b Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 16 Jan 2020 22:53:11 -0700 Subject: [PATCH 006/101] Use parent pom 3.56 to fix JTH test issue Now allowed to run parallel tests on multi-core machines without hanging. --- pom.xml | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/pom.xml b/pom.xml index b1ed97d639..8cbd5c009a 100644 --- a/pom.xml +++ b/pom.xml @@ -4,7 +4,7 @@ org.jenkins-ci.plugins plugin - 3.55 + 3.56 @@ -31,13 +31,10 @@ 8 false true - 1 + 1C false 1.35 - - - 2.60 - + From d6e761dad5df49fdd1a8da508139b513623fe111 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sat, 2 Nov 2019 13:55:47 -0600 Subject: [PATCH 007/101] [JENKINS-42860] Whitelist pipeline safe getters Pipelines are not allowed to reference plugin fields unless those fields are whitelisted. Allow plugin access to many fields in the git plugin. Test automation of this change uses an acceptance test rather than a test included inside this repository. There are suggestions from the community that test automation of a whitelisted method should be feasible, but I didn't want to delay the release of git plugin 4.1.0 for that automation inside the plugin when there is already automation outside the plugin. See the acceptance test docker image at: https://github.com/MarkEWaite/docker-lfs/tree/lts-with-plugins See the acceptance test source code at: https://github.com/MarkEWaite/jenkins-bugs/blob/JENKINS-42860/Jenkinsfile --- pom.xml | 9 ++++----- src/main/java/hudson/plugins/git/BranchSpec.java | 2 ++ src/main/java/hudson/plugins/git/GitSCM.java | 10 ++++++++++ .../plugins/git/GitSCMBackwardCompatibility.java | 2 ++ src/main/java/hudson/plugins/git/SubmoduleConfig.java | 2 ++ src/main/java/hudson/plugins/git/UserMergeOptions.java | 3 +++ src/main/java/hudson/plugins/git/UserRemoteConfig.java | 6 ++++++ .../plugins/git/extensions/impl/CloneOption.java | 7 +++++++ .../plugins/git/extensions/impl/LocalBranch.java | 2 ++ .../plugins/git/extensions/impl/PreBuildMerge.java | 2 ++ .../git/extensions/impl/SparseCheckoutPath.java | 2 ++ .../git/extensions/impl/SparseCheckoutPaths.java | 2 ++ .../plugins/git/extensions/impl/SubmoduleOption.java | 10 ++++++++++ 13 files changed, 54 insertions(+), 5 deletions(-) diff --git a/pom.xml b/pom.xml index 8cbd5c009a..2c458dabfa 100644 --- a/pom.xml +++ b/pom.xml @@ -98,6 +98,10 @@ org.jenkins-ci.plugins scm-api + + org.jenkins-ci.plugins + script-security + org.jenkins-ci.plugins.workflow workflow-step-api @@ -121,11 +125,6 @@ junit test - - org.jenkins-ci.plugins - script-security - test - org.hamcrest hamcrest-core diff --git a/src/main/java/hudson/plugins/git/BranchSpec.java b/src/main/java/hudson/plugins/git/BranchSpec.java index 606a40d644..51bdae2b92 100644 --- a/src/main/java/hudson/plugins/git/BranchSpec.java +++ b/src/main/java/hudson/plugins/git/BranchSpec.java @@ -15,6 +15,7 @@ import java.util.StringTokenizer; import java.util.regex.Matcher; import java.util.regex.Pattern; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.kohsuke.stapler.export.Exported; import org.kohsuke.stapler.export.ExportedBean; @@ -38,6 +39,7 @@ public class BranchSpec extends AbstractDescribableImpl implements S private String name; @Exported + @Whitelisted public String getName() { return name; } diff --git a/src/main/java/hudson/plugins/git/GitSCM.java b/src/main/java/hudson/plugins/git/GitSCM.java index b5d838fc6b..9aa053790b 100644 --- a/src/main/java/hudson/plugins/git/GitSCM.java +++ b/src/main/java/hudson/plugins/git/GitSCM.java @@ -73,6 +73,7 @@ import org.jenkinsci.plugins.gitclient.FetchCommand; import org.jenkinsci.plugins.gitclient.Git; import org.jenkinsci.plugins.gitclient.GitClient; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.StaplerRequest; import org.kohsuke.stapler.export.Exported; @@ -161,6 +162,7 @@ public class GitSCM extends GitSCMBackwardCompatibility { @SuppressFBWarnings(value="SE_BAD_FIELD", justification="Known non-serializable field") private DescribableList extensions; + @Whitelisted public Collection getSubmoduleCfg() { return submoduleCfg; } @@ -236,6 +238,7 @@ public GitSCM( * * @since 2.0 */ + @Whitelisted public DescribableList getExtensions() { return extensions; } @@ -347,6 +350,7 @@ public Object readResolve() throws IOException { } @Override + @Whitelisted public GitRepositoryBrowser getBrowser() { return browser; } @@ -429,6 +433,7 @@ public boolean isUseExistingAccountWithSameEmail() { return (gitDescriptor != null && gitDescriptor.isUseExistingAccountWithSameEmail()); } + @Whitelisted public BuildChooser getBuildChooser() { BuildChooser bc; @@ -518,6 +523,7 @@ public RemoteConfig getRepositoryByName(String repoName) { } @Exported + @Whitelisted public List getUserRemoteConfigs() { if (userRemoteConfigs == null) { /* Prevent NPE when no remote config defined */ @@ -526,6 +532,7 @@ public List getUserRemoteConfigs() { return Collections.unmodifiableList(userRemoteConfigs); } + @Whitelisted public List getRepositories() { // Handle null-value to ensure backwards-compatibility, ie project configuration missing the XML element if (remoteRepositories == null) { @@ -570,6 +577,7 @@ public String deriveLocalBranchName(String remoteBranchName) { } @CheckForNull + @Whitelisted public String getGitTool() { return gitTool; } @@ -1694,11 +1702,13 @@ public void populateEnvironmentVariables(Map env) { private static final long serialVersionUID = 1L; + @Whitelisted public boolean isDoGenerateSubmoduleConfigurations() { return this.doGenerateSubmoduleConfigurations; } @Exported + @Whitelisted public List getBranches() { return branches; } diff --git a/src/main/java/hudson/plugins/git/GitSCMBackwardCompatibility.java b/src/main/java/hudson/plugins/git/GitSCMBackwardCompatibility.java index 6a1cd394ae..408e9cb57d 100644 --- a/src/main/java/hudson/plugins/git/GitSCMBackwardCompatibility.java +++ b/src/main/java/hudson/plugins/git/GitSCMBackwardCompatibility.java @@ -17,6 +17,7 @@ import java.util.Set; import static org.apache.commons.lang.StringUtils.isNotBlank; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; /** * This is a portion of {@link GitSCM} for the stuff that's used to be in {@link GitSCM} @@ -178,6 +179,7 @@ public abstract class GitSCMBackwardCompatibility extends SCM implements Seriali private transient BuildChooser buildChooser; + @Whitelisted abstract DescribableList getExtensions(); @Override diff --git a/src/main/java/hudson/plugins/git/SubmoduleConfig.java b/src/main/java/hudson/plugins/git/SubmoduleConfig.java index 1223254b8e..fa0b023f32 100644 --- a/src/main/java/hudson/plugins/git/SubmoduleConfig.java +++ b/src/main/java/hudson/plugins/git/SubmoduleConfig.java @@ -2,6 +2,7 @@ import com.google.common.base.Joiner; import org.apache.commons.collections.CollectionUtils; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.kohsuke.stapler.DataBoundConstructor; import java.util.Arrays; @@ -31,6 +32,7 @@ public SubmoduleConfig(String submoduleName, Collection branches) { } } + @Whitelisted public String getSubmoduleName() { return submoduleName; } diff --git a/src/main/java/hudson/plugins/git/UserMergeOptions.java b/src/main/java/hudson/plugins/git/UserMergeOptions.java index 4a45c5f4ca..e4ff9915a2 100644 --- a/src/main/java/hudson/plugins/git/UserMergeOptions.java +++ b/src/main/java/hudson/plugins/git/UserMergeOptions.java @@ -13,6 +13,7 @@ import java.util.Locale; import java.util.Map; import java.util.Objects; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.jenkinsci.plugins.structs.describable.CustomDescribableModel; import org.kohsuke.stapler.DataBoundSetter; @@ -70,6 +71,7 @@ public UserMergeOptions(PreBuildMergeOptions pbm) { * Repository name, such as 'origin' that designates which repository the branch lives in. * @return repository name */ + @Whitelisted public String getMergeRemote() { return mergeRemote; } @@ -84,6 +86,7 @@ public void setMergeRemote(String mergeRemote) { * Normally a branch name like 'master'. * @return branch name from which merge will be performed */ + @Whitelisted public String getMergeTarget() { return mergeTarget; } diff --git a/src/main/java/hudson/plugins/git/UserRemoteConfig.java b/src/main/java/hudson/plugins/git/UserRemoteConfig.java index 8ed04dcb87..72abac2a0c 100644 --- a/src/main/java/hudson/plugins/git/UserRemoteConfig.java +++ b/src/main/java/hudson/plugins/git/UserRemoteConfig.java @@ -39,6 +39,7 @@ import static hudson.Util.fixEmpty; import static hudson.Util.fixEmptyAndTrim; import hudson.model.FreeStyleProject; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.kohsuke.stapler.interceptor.RequirePOST; @ExportedBean @@ -58,27 +59,32 @@ public UserRemoteConfig(String url, String name, String refspec, @CheckForNull S } @Exported + @Whitelisted public String getName() { return name; } @Exported + @Whitelisted public String getRefspec() { return refspec; } @Exported @CheckForNull + @Whitelisted public String getUrl() { return url; } @Exported + @Whitelisted @CheckForNull public String getCredentialsId() { return credentialsId; } + @Override public String toString() { return getRefspec() + " => " + getUrl() + " (" + getName() + ")"; } diff --git a/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java b/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java index 6a0fc44df5..be46f4339b 100644 --- a/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java +++ b/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java @@ -21,6 +21,7 @@ import org.jenkinsci.plugins.gitclient.CloneCommand; import org.jenkinsci.plugins.gitclient.FetchCommand; import org.jenkinsci.plugins.gitclient.GitClient; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.DataBoundSetter; @@ -48,10 +49,12 @@ public CloneOption(boolean shallow, boolean noTags, String reference, Integer ti this.honorRefspec = false; } + @Whitelisted public boolean isShallow() { return shallow; } + @Whitelisted public boolean isNoTags() { return noTags; } @@ -94,14 +97,17 @@ public void setHonorRefspec(boolean honorRefspec) { * * @return true if initial clone will honor the user defined refspec */ + @Whitelisted public boolean isHonorRefspec() { return honorRefspec; } + @Whitelisted public String getReference() { return reference; } + @Whitelisted public Integer getTimeout() { return timeout; } @@ -111,6 +117,7 @@ public void setDepth(Integer depth) { this.depth = depth; } + @Whitelisted public Integer getDepth() { return depth; } diff --git a/src/main/java/hudson/plugins/git/extensions/impl/LocalBranch.java b/src/main/java/hudson/plugins/git/extensions/impl/LocalBranch.java index 2374793d66..d44512f010 100644 --- a/src/main/java/hudson/plugins/git/extensions/impl/LocalBranch.java +++ b/src/main/java/hudson/plugins/git/extensions/impl/LocalBranch.java @@ -7,6 +7,7 @@ import hudson.plugins.git.extensions.FakeGitSCMExtension; import hudson.plugins.git.extensions.GitSCMExtensionDescriptor; import java.util.Objects; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.kohsuke.stapler.DataBoundConstructor; /** @@ -28,6 +29,7 @@ public LocalBranch(@CheckForNull String localBranch) { } @CheckForNull + @Whitelisted public String getLocalBranch() { return localBranch; } diff --git a/src/main/java/hudson/plugins/git/extensions/impl/PreBuildMerge.java b/src/main/java/hudson/plugins/git/extensions/impl/PreBuildMerge.java index 20881cb18e..d0bd426941 100644 --- a/src/main/java/hudson/plugins/git/extensions/impl/PreBuildMerge.java +++ b/src/main/java/hudson/plugins/git/extensions/impl/PreBuildMerge.java @@ -18,6 +18,7 @@ import org.jenkinsci.plugins.gitclient.CheckoutCommand; import org.jenkinsci.plugins.gitclient.GitClient; import org.jenkinsci.plugins.gitclient.MergeCommand; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.kohsuke.stapler.DataBoundConstructor; import java.io.IOException; @@ -47,6 +48,7 @@ public PreBuildMerge(UserMergeOptions options) { this.options = options; } + @Whitelisted public UserMergeOptions getOptions() { return options; } diff --git a/src/main/java/hudson/plugins/git/extensions/impl/SparseCheckoutPath.java b/src/main/java/hudson/plugins/git/extensions/impl/SparseCheckoutPath.java index e3d67e22ca..cbad96c4f0 100644 --- a/src/main/java/hudson/plugins/git/extensions/impl/SparseCheckoutPath.java +++ b/src/main/java/hudson/plugins/git/extensions/impl/SparseCheckoutPath.java @@ -5,6 +5,7 @@ import hudson.model.AbstractDescribableImpl; import hudson.model.Descriptor; import jenkins.model.Jenkins; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.kohsuke.stapler.DataBoundConstructor; import java.io.Serializable; @@ -23,6 +24,7 @@ public SparseCheckoutPath(String path) { this.path = path; } + @Whitelisted public String getPath() { return path; } diff --git a/src/main/java/hudson/plugins/git/extensions/impl/SparseCheckoutPaths.java b/src/main/java/hudson/plugins/git/extensions/impl/SparseCheckoutPaths.java index 6bed12a0bd..ba211c1db6 100644 --- a/src/main/java/hudson/plugins/git/extensions/impl/SparseCheckoutPaths.java +++ b/src/main/java/hudson/plugins/git/extensions/impl/SparseCheckoutPaths.java @@ -11,6 +11,7 @@ import org.jenkinsci.plugins.gitclient.CheckoutCommand; import org.jenkinsci.plugins.gitclient.CloneCommand; import org.jenkinsci.plugins.gitclient.GitClient; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.kohsuke.stapler.DataBoundConstructor; import java.io.IOException; @@ -26,6 +27,7 @@ public SparseCheckoutPaths(List sparseCheckoutPaths) { this.sparseCheckoutPaths = sparseCheckoutPaths == null ? Collections.emptyList() : sparseCheckoutPaths; } + @Whitelisted public List getSparseCheckoutPaths() { return sparseCheckoutPaths; } diff --git a/src/main/java/hudson/plugins/git/extensions/impl/SubmoduleOption.java b/src/main/java/hudson/plugins/git/extensions/impl/SubmoduleOption.java index 6a6b94877e..292a3746c1 100644 --- a/src/main/java/hudson/plugins/git/extensions/impl/SubmoduleOption.java +++ b/src/main/java/hudson/plugins/git/extensions/impl/SubmoduleOption.java @@ -14,6 +14,7 @@ import java.util.Objects; import org.jenkinsci.plugins.gitclient.GitClient; import org.jenkinsci.plugins.gitclient.SubmoduleUpdateCommand; +import org.jenkinsci.plugins.scriptsecurity.sandbox.whitelists.Whitelisted; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.DataBoundSetter; @@ -59,26 +60,32 @@ public SubmoduleOption(boolean disableSubmodules, boolean recursiveSubmodules, b this.timeout = timeout; } + @Whitelisted public boolean isDisableSubmodules() { return disableSubmodules; } + @Whitelisted public boolean isRecursiveSubmodules() { return recursiveSubmodules; } + @Whitelisted public boolean isTrackingSubmodules() { return trackingSubmodules; } + @Whitelisted public boolean isParentCredentials() { return parentCredentials; } + @Whitelisted public String getReference() { return reference; } + @Whitelisted public Integer getTimeout() { return timeout; } @@ -88,6 +95,7 @@ public void setShallow(boolean shallow) { this.shallow = shallow; } + @Whitelisted public boolean getShallow() { return shallow; } @@ -97,10 +105,12 @@ public void setDepth(Integer depth) { this.depth = depth; } + @Whitelisted public Integer getDepth() { return depth; } + @Whitelisted public Integer getThreads() { return threads; } From d0299017641159f47210a0bd24a079ce01a4232c Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Wed, 8 Jan 2020 04:35:47 -0700 Subject: [PATCH 008/101] Add repository browser details doc --- README.adoc | 276 +++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 275 insertions(+), 1 deletion(-) diff --git a/README.adoc b/README.adoc index 70fc13e559..f53aa433d0 100644 --- a/README.adoc +++ b/README.adoc @@ -99,7 +99,281 @@ JGit becomes available throughout Jenkins once it has been enabled. [[repository-browser]] === Repository Browser -A Repository Browser adds links in "changes" views within Jenkins to an external system for browsing the details of those changes. The "Auto" selection attempts to infer the repository browser from the "Repository URL" and can detect Cloud versions of GitHub, Bitbucket and GitLab. +A Repository Browser adds links in "changes" views within Jenkins to an external system for browsing the details of those changes. +The "Auto" selection attempts to infer the repository browser from the "Repository URL" and can detect Cloud versions of GitHub, Bitbucket and GitLab. + +Repository browsers include: + +[[assemblaweb-repository-browser]] +=== AssemblaWeb + +Repository browser for git repositories hosted by link:https://www.assembla.com/home[Assembla]. +Options include: + +[[assembla-git-url]] +Assembla Git URL:: + + Root URL serving this Assembla repository. + For example, \https://app.assembla.com/spaces/git-plugin/git/source + +[[fisheye-repository-browser]] +=== FishEye + +Repository browser for git repositories hosted by link:https://www.atlassian.com/software/fisheye[Atlassian Fisheye]. +Options include: + +[[fisheye-url]] +URL:: + + Root URL serving this FishEye repository. + For example, \https://fisheye.example.com/browser/my-project + +[[gitlab-com-repository-browser]] +=== GitLab + +Repository browser for git repositories hosted on link:https://gitlab.com[GitLab.com]. +No options can be configured for this repository browser. +Users hosting their own instances of GitLab should use the <>. + +[[gitea-repository-browser]] +=== Gitea + +Repository browser for git repositories hosted by link:https://gitea.io/[Gitea]. +Options include: + +[[gitea-url]] +Repository URL:: + + Root URL serving this gitea repository. + For example, \https://gitea.example.com/username/project-name + +[[kiln-repository-browser]] +=== Kiln + +Repository browser for git repositories hosted by link:http://www.fogbugz.com/version-control[Kiln]. +Options include: + +[[kiln-url]] +URL:: + + Root URL serving this Kiln repository. + For example, \https://kiln.example.com/username/my-project + +[[visual-studio-team-services-repository-browser]] +=== Microsoft Team Foundation Server/Visual Studio Team Services + +Repository browser for git repositories hosted by link:https://azure.microsoft.com/en-us/solutions/devops/[Azure DevOps]. +Options include: + +[[visual-studio-repository-url-or-name]] +URL or name:: + + Root URL serving this Azure DevOps repository. + For example, \https://example.visualstudio.com/_git/my-project. + +[[bitbucketweb-repository-browser]] +=== bitbucketweb + +Repository browser for git repositories hosted by link:https://bitbucket.org/[Bitbucket]. +Options include: + +[[bitbucketweb-url]] +URL:: + + Root URL serving this Bitbucket repository. + For example, \https://bitbucket.example.com/username/my-project + +[[cgit-repository-browser]] +=== cgit + +Repository browser for git repositories hosted by link:https://git.zx2c4.com/cgit/[cgit]. +Options include: + +[[cgit-url]] +URL:: + + Root URL serving this cgit repository. + For example, \https://git.zx2c4.com/cgit/ + +[[gitblit-repository-browser]] +=== gitblit + +[[gitblit-url]] +GitBlit root url:: + + Root URL serving this GitBlit repository. + For example, \https://gitblit.example.com/cgit/ + +[[gitblit-project-name]] +Project name in GitBlit:: + + Name of the GitBlit project. + For example, `my-project` + +[[githubweb-repository-browser]] +=== githubweb + +Repository browser for git repositories hosted by link:https://github.com//[GitHub]. +Options include: + +[[githubweb-url]] +GitHub root url:: + + Root URL serving this GitHub repository. + For example, \https://github.example.com/username/my-project + +[[gitiles-repository-browser]] +=== gitiles + +Repository browser for git repositories hosted by link:https://gerrit.googlesource.com/gitiles/[Gitiles]. +Options include: + +[[githubweb-url]] +gitiles root url:: + + Root URL serving this Gitiles repository. + For example, \https://gerrit.googlesource.com/gitiles/ + +[[gitlab-self-hosted-repository-browser]] +=== gitlab + +Repository browser for git repositories hosted by link:https://gitlab.com/[GitLab]. +Options include: + +[[gitlab-url]] +URL:: + + Root URL serving this GitLab repository. + For example, \https://gitlab.example.com/username/my-project + +[[gitlab-version]] +Version:: + + Major and minor version of GitLab you use, such as 12.6. + If you don't specify a version, a modern version of GitLab (>= 8.0) is assumed. + For example, `12.6` + +[[gitlist-repository-browser]] +=== gitlist + +Repository browser for git repositories hosted by link:https://gitlist.org/[GitList]. +Options include: + +[[gitlist-url]] +URL:: + + Root URL serving this GitList repository. + For example, \https://gitlist.example.com/username/my-project + +[[gitoriousweb-repository-browser]] +=== gitoriousweb + +Gitorious was acquired in 2015. +This browser is *deprecated*. + +[[gitoriousweb-url]] +URL:: + + Root URL serving this Gitorious repository. + For example, \https://gitorious.org/username/my-project + +[[gitweb-repository-browser]] +=== gitweb + +Repository browser for git repositories hosted by link:https://git-scm.com/docs/gitweb[GitWeb]. +Options include: + +[[gitweb-url]] +URL:: + + Root URL serving this GitWeb repository. + For example, \https://gitweb.example.com/username/my-project + +[[gogs-repository-browser]] +=== gogs + +Repository browser for git repositories hosted by link:https://gogs.io/[Gogs]. +Options include: + +[[gogs-url]] +URL:: + + Root URL serving this Gogs repository. + For example, \https://gogs.example.com/username/my-project + +[[phabricator-repository-browser]] +=== phabricator + +Repository browser for git repositories hosted by link:https://www.phacility.com/phabricator/[Phacility Phabricator]. +Options include: + +[[phabricator-url]] +URL:: + + Root URL serving this Phabricator repository. + For example, \https://phabricator.example.com/ + +[[phabricator-repository-name]] +Repository name in Phab:: + + Name of the Phabricator repository. + For example, `my-project` + +[[redmineweb-repository-browser]] +=== redmineweb + +Repository browser for git repositories hosted by link:https://www.redmine.org/[Redmine]. +Options include: + +[[redmineweb-url]] +URL:: + + Root URL serving this Redmine repository. + For example, \https://redmine.example.com/username/projects/my-project/repository + +[[rhodecode-repository-browser]] +=== rhodecode + +Repository browser for git repositories hosted by link:https://thodecode.com/[RhodeCode]. +Options include: + +[[rhodecode-url]] +URL:: + + Root URL serving this RhodeCode repository. + For example, \https://rhodecode.example.com/username/my-project + +[[stash-repository-browser]] +=== stash + +Stash is now called *BitBucket Server*. +Repository browser for git repositories hosted by link:https://www.atlassian.com/software/bitbucket[BitBucket Server]. +Options include: + +stash +[[stash-url]] +URL:: + + Root URL serving this Stash repository. + For example, \https://stash.example.com/username/my-project + +[[viewgit-repository-browser]] +=== viewgit + +Repository browser for git repositories hosted by link:https://www.openhub.net/p/viewgit[viewgit]. +Options include: + +[[viewgit-root-url]] +ViewGit root url:: + + Root URL serving this ViewGit repository. + For example, \https://viewgit.example.com/ + +[[viewgit-project-name]] +Project Name in ViewGit:: + + ViewGit project name. + For example, `my-project` [[extensions]] == Extensions From 254394aec7114ec14dd47e2c0767f092ea6d4370 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sat, 18 Jan 2020 06:36:46 -0700 Subject: [PATCH 009/101] Repository browser docs at heading 4, not 3 --- README.adoc | 42 +++++++++++++++++++++--------------------- 1 file changed, 21 insertions(+), 21 deletions(-) diff --git a/README.adoc b/README.adoc index f53aa433d0..390169cb28 100644 --- a/README.adoc +++ b/README.adoc @@ -105,7 +105,7 @@ The "Auto" selection attempts to infer the repository browser from the "Reposito Repository browsers include: [[assemblaweb-repository-browser]] -=== AssemblaWeb +==== AssemblaWeb Repository browser for git repositories hosted by link:https://www.assembla.com/home[Assembla]. Options include: @@ -117,7 +117,7 @@ Assembla Git URL:: For example, \https://app.assembla.com/spaces/git-plugin/git/source [[fisheye-repository-browser]] -=== FishEye +==== FishEye Repository browser for git repositories hosted by link:https://www.atlassian.com/software/fisheye[Atlassian Fisheye]. Options include: @@ -129,14 +129,14 @@ URL:: For example, \https://fisheye.example.com/browser/my-project [[gitlab-com-repository-browser]] -=== GitLab +==== GitLab Repository browser for git repositories hosted on link:https://gitlab.com[GitLab.com]. No options can be configured for this repository browser. Users hosting their own instances of GitLab should use the <>. [[gitea-repository-browser]] -=== Gitea +==== Gitea Repository browser for git repositories hosted by link:https://gitea.io/[Gitea]. Options include: @@ -148,7 +148,7 @@ Repository URL:: For example, \https://gitea.example.com/username/project-name [[kiln-repository-browser]] -=== Kiln +==== Kiln Repository browser for git repositories hosted by link:http://www.fogbugz.com/version-control[Kiln]. Options include: @@ -160,7 +160,7 @@ URL:: For example, \https://kiln.example.com/username/my-project [[visual-studio-team-services-repository-browser]] -=== Microsoft Team Foundation Server/Visual Studio Team Services +==== Microsoft Team Foundation Server/Visual Studio Team Services Repository browser for git repositories hosted by link:https://azure.microsoft.com/en-us/solutions/devops/[Azure DevOps]. Options include: @@ -172,7 +172,7 @@ URL or name:: For example, \https://example.visualstudio.com/_git/my-project. [[bitbucketweb-repository-browser]] -=== bitbucketweb +==== bitbucketweb Repository browser for git repositories hosted by link:https://bitbucket.org/[Bitbucket]. Options include: @@ -184,7 +184,7 @@ URL:: For example, \https://bitbucket.example.com/username/my-project [[cgit-repository-browser]] -=== cgit +==== cgit Repository browser for git repositories hosted by link:https://git.zx2c4.com/cgit/[cgit]. Options include: @@ -196,7 +196,7 @@ URL:: For example, \https://git.zx2c4.com/cgit/ [[gitblit-repository-browser]] -=== gitblit +==== gitblit [[gitblit-url]] GitBlit root url:: @@ -211,7 +211,7 @@ Project name in GitBlit:: For example, `my-project` [[githubweb-repository-browser]] -=== githubweb +==== githubweb Repository browser for git repositories hosted by link:https://github.com//[GitHub]. Options include: @@ -223,7 +223,7 @@ GitHub root url:: For example, \https://github.example.com/username/my-project [[gitiles-repository-browser]] -=== gitiles +==== gitiles Repository browser for git repositories hosted by link:https://gerrit.googlesource.com/gitiles/[Gitiles]. Options include: @@ -235,7 +235,7 @@ gitiles root url:: For example, \https://gerrit.googlesource.com/gitiles/ [[gitlab-self-hosted-repository-browser]] -=== gitlab +==== gitlab Repository browser for git repositories hosted by link:https://gitlab.com/[GitLab]. Options include: @@ -254,7 +254,7 @@ Version:: For example, `12.6` [[gitlist-repository-browser]] -=== gitlist +==== gitlist Repository browser for git repositories hosted by link:https://gitlist.org/[GitList]. Options include: @@ -266,7 +266,7 @@ URL:: For example, \https://gitlist.example.com/username/my-project [[gitoriousweb-repository-browser]] -=== gitoriousweb +==== gitoriousweb Gitorious was acquired in 2015. This browser is *deprecated*. @@ -278,7 +278,7 @@ URL:: For example, \https://gitorious.org/username/my-project [[gitweb-repository-browser]] -=== gitweb +==== gitweb Repository browser for git repositories hosted by link:https://git-scm.com/docs/gitweb[GitWeb]. Options include: @@ -290,7 +290,7 @@ URL:: For example, \https://gitweb.example.com/username/my-project [[gogs-repository-browser]] -=== gogs +==== gogs Repository browser for git repositories hosted by link:https://gogs.io/[Gogs]. Options include: @@ -302,7 +302,7 @@ URL:: For example, \https://gogs.example.com/username/my-project [[phabricator-repository-browser]] -=== phabricator +==== phabricator Repository browser for git repositories hosted by link:https://www.phacility.com/phabricator/[Phacility Phabricator]. Options include: @@ -320,7 +320,7 @@ Repository name in Phab:: For example, `my-project` [[redmineweb-repository-browser]] -=== redmineweb +==== redmineweb Repository browser for git repositories hosted by link:https://www.redmine.org/[Redmine]. Options include: @@ -332,7 +332,7 @@ URL:: For example, \https://redmine.example.com/username/projects/my-project/repository [[rhodecode-repository-browser]] -=== rhodecode +==== rhodecode Repository browser for git repositories hosted by link:https://thodecode.com/[RhodeCode]. Options include: @@ -344,7 +344,7 @@ URL:: For example, \https://rhodecode.example.com/username/my-project [[stash-repository-browser]] -=== stash +==== stash Stash is now called *BitBucket Server*. Repository browser for git repositories hosted by link:https://www.atlassian.com/software/bitbucket[BitBucket Server]. @@ -358,7 +358,7 @@ URL:: For example, \https://stash.example.com/username/my-project [[viewgit-repository-browser]] -=== viewgit +==== viewgit Repository browser for git repositories hosted by link:https://www.openhub.net/p/viewgit[viewgit]. Options include: From 8ae513fdca2785aab25a99cad7637a6412d16b79 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sat, 18 Jan 2020 06:42:10 -0700 Subject: [PATCH 010/101] Correct typo in README branch name --- README.adoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.adoc b/README.adoc index 390169cb28..9c40bf6e07 100644 --- a/README.adoc +++ b/README.adoc @@ -538,7 +538,7 @@ Branch name:: If given, checkout the revision to build as HEAD on the named branch. If value is an empty string or "**", then the branch name is computed from the remote branch without the origin. - In that case, a remote branch 'origin/master' will be checked out to a local branch named 'master', and a remote branch 'origin/develop/new-feature' will be checked out to a local branch named 'develop/newfeature'. + In that case, a remote branch 'origin/master' will be checked out to a local branch named 'master', and a remote branch 'origin/develop/new-feature' will be checked out to a local branch named 'develop/new-feature'. [[wipe-out-repository-and-force-clone]] ==== Wipe out repository and force clone From c2f3ce2d540fb078def4fc2726442f74c1b05fd4 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sat, 18 Jan 2020 06:53:12 -0700 Subject: [PATCH 011/101] Place examples in code blocks --- README.adoc | 42 +++++++++++++++++++++--------------------- 1 file changed, 21 insertions(+), 21 deletions(-) diff --git a/README.adoc b/README.adoc index 9c40bf6e07..9f857b7bbb 100644 --- a/README.adoc +++ b/README.adoc @@ -114,7 +114,7 @@ Options include: Assembla Git URL:: Root URL serving this Assembla repository. - For example, \https://app.assembla.com/spaces/git-plugin/git/source + For example, `\https://app.assembla.com/spaces/git-plugin/git/source` [[fisheye-repository-browser]] ==== FishEye @@ -126,14 +126,14 @@ Options include: URL:: Root URL serving this FishEye repository. - For example, \https://fisheye.example.com/browser/my-project + For example, `\https://fisheye.example.com/browser/my-project` [[gitlab-com-repository-browser]] ==== GitLab Repository browser for git repositories hosted on link:https://gitlab.com[GitLab.com]. No options can be configured for this repository browser. -Users hosting their own instances of GitLab should use the <>. +Users hosting their own instances of GitLab should use the <> browser instead. [[gitea-repository-browser]] ==== Gitea @@ -145,7 +145,7 @@ Options include: Repository URL:: Root URL serving this gitea repository. - For example, \https://gitea.example.com/username/project-name + For example, `\https://gitea.example.com/username/project-name` [[kiln-repository-browser]] ==== Kiln @@ -157,7 +157,7 @@ Options include: URL:: Root URL serving this Kiln repository. - For example, \https://kiln.example.com/username/my-project + For example, `\https://kiln.example.com/username/my-project` [[visual-studio-team-services-repository-browser]] ==== Microsoft Team Foundation Server/Visual Studio Team Services @@ -169,7 +169,7 @@ Options include: URL or name:: Root URL serving this Azure DevOps repository. - For example, \https://example.visualstudio.com/_git/my-project. + For example, `\https://example.visualstudio.com/_git/my-project.` [[bitbucketweb-repository-browser]] ==== bitbucketweb @@ -181,7 +181,7 @@ Options include: URL:: Root URL serving this Bitbucket repository. - For example, \https://bitbucket.example.com/username/my-project + For example, `\https://bitbucket.example.com/username/my-project` [[cgit-repository-browser]] ==== cgit @@ -193,7 +193,7 @@ Options include: URL:: Root URL serving this cgit repository. - For example, \https://git.zx2c4.com/cgit/ + For example, `\https://git.zx2c4.com/cgit/` [[gitblit-repository-browser]] ==== gitblit @@ -202,7 +202,7 @@ URL:: GitBlit root url:: Root URL serving this GitBlit repository. - For example, \https://gitblit.example.com/cgit/ + For example, `\https://gitblit.example.com/cgit/` [[gitblit-project-name]] Project name in GitBlit:: @@ -220,7 +220,7 @@ Options include: GitHub root url:: Root URL serving this GitHub repository. - For example, \https://github.example.com/username/my-project + For example, `\https://github.example.com/username/my-project` [[gitiles-repository-browser]] ==== gitiles @@ -232,7 +232,7 @@ Options include: gitiles root url:: Root URL serving this Gitiles repository. - For example, \https://gerrit.googlesource.com/gitiles/ + For example, `\https://gerrit.googlesource.com/gitiles/` [[gitlab-self-hosted-repository-browser]] ==== gitlab @@ -244,7 +244,7 @@ Options include: URL:: Root URL serving this GitLab repository. - For example, \https://gitlab.example.com/username/my-project + For example, `\https://gitlab.example.com/username/my-project` [[gitlab-version]] Version:: @@ -263,7 +263,7 @@ Options include: URL:: Root URL serving this GitList repository. - For example, \https://gitlist.example.com/username/my-project + For example, `\https://gitlist.example.com/username/my-project` [[gitoriousweb-repository-browser]] ==== gitoriousweb @@ -275,7 +275,7 @@ This browser is *deprecated*. URL:: Root URL serving this Gitorious repository. - For example, \https://gitorious.org/username/my-project + For example, `\https://gitorious.org/username/my-project` [[gitweb-repository-browser]] ==== gitweb @@ -287,7 +287,7 @@ Options include: URL:: Root URL serving this GitWeb repository. - For example, \https://gitweb.example.com/username/my-project + For example, `\https://gitweb.example.com/username/my-project` [[gogs-repository-browser]] ==== gogs @@ -299,7 +299,7 @@ Options include: URL:: Root URL serving this Gogs repository. - For example, \https://gogs.example.com/username/my-project + For example, `\https://gogs.example.com/username/my-project` [[phabricator-repository-browser]] ==== phabricator @@ -311,7 +311,7 @@ Options include: URL:: Root URL serving this Phabricator repository. - For example, \https://phabricator.example.com/ + For example, `\https://phabricator.example.com/` [[phabricator-repository-name]] Repository name in Phab:: @@ -329,7 +329,7 @@ Options include: URL:: Root URL serving this Redmine repository. - For example, \https://redmine.example.com/username/projects/my-project/repository + For example, `\https://redmine.example.com/username/projects/my-project/repository` [[rhodecode-repository-browser]] ==== rhodecode @@ -341,7 +341,7 @@ Options include: URL:: Root URL serving this RhodeCode repository. - For example, \https://rhodecode.example.com/username/my-project + For example, `\https://rhodecode.example.com/username/my-project` [[stash-repository-browser]] ==== stash @@ -355,7 +355,7 @@ stash URL:: Root URL serving this Stash repository. - For example, \https://stash.example.com/username/my-project + For example, `\https://stash.example.com/username/my-project` [[viewgit-repository-browser]] ==== viewgit @@ -367,7 +367,7 @@ Options include: ViewGit root url:: Root URL serving this ViewGit repository. - For example, \https://viewgit.example.com/ + For example, `\https://viewgit.example.com/` [[viewgit-project-name]] Project Name in ViewGit:: From 34b3bb607d946cf582b8773ec42bb37d0190946d Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sat, 18 Jan 2020 09:35:58 -0700 Subject: [PATCH 012/101] Use only 3 parallel test processes When using 1C, all cores on a 72 core machine cause machine out of memory --- pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 2c458dabfa..934e728455 100644 --- a/pom.xml +++ b/pom.xml @@ -31,7 +31,7 @@ 8 false true - 1C + 3 false 1.35 From 2a411c1d9c9bbfc070b4f2035dfad9d0067d5f29 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sat, 18 Jan 2020 11:12:25 -0700 Subject: [PATCH 013/101] [maven-release-plugin] prepare release git-4.1.0 --- pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index 934e728455..e573f3cb32 100644 --- a/pom.xml +++ b/pom.xml @@ -17,7 +17,7 @@ git - ${revision}${changelist} + 4.1.0 hpi Jenkins Git plugin Integrates Jenkins with GIT SCM @@ -272,7 +272,7 @@ scm:git:git://github.com/jenkinsci/${project.artifactId}-plugin.git scm:git:git@github.com:jenkinsci/${project.artifactId}-plugin.git https://github.com/jenkinsci/${project.artifactId}-plugin - ${scmTag} + git-4.1.0 From c839a9c27f1f7f52c55c978b2cb85ba04a168a43 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sat, 18 Jan 2020 11:12:38 -0700 Subject: [PATCH 014/101] [maven-release-plugin] prepare for next development iteration --- pom.xml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/pom.xml b/pom.xml index e573f3cb32..4e6736a1f0 100644 --- a/pom.xml +++ b/pom.xml @@ -17,7 +17,7 @@ git - 4.1.0 + ${revision}${changelist} hpi Jenkins Git plugin Integrates Jenkins with GIT SCM @@ -25,7 +25,7 @@ 2007 - 4.1.0 + 4.1.1 -SNAPSHOT 2.138.4 8 @@ -272,7 +272,7 @@ scm:git:git://github.com/jenkinsci/${project.artifactId}-plugin.git scm:git:git@github.com:jenkinsci/${project.artifactId}-plugin.git https://github.com/jenkinsci/${project.artifactId}-plugin - git-4.1.0 + ${scmTag} From 15fc5c47d1b6e728222c86277841c6aa367df17b Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sun, 19 Jan 2020 13:20:52 -0700 Subject: [PATCH 015/101] Correct URL to docs --- pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 4e6736a1f0..3fa1c149cd 100644 --- a/pom.xml +++ b/pom.xml @@ -21,7 +21,7 @@ hpi Jenkins Git plugin Integrates Jenkins with GIT SCM - https://github.com/jenkinsci/git-plugin/README.adoc + https://github.com/jenkinsci/git-plugin/blob/master/README.adoc 2007 From de5f29f8b36d1463c60f8609e016bc1a2e156f16 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sun, 19 Jan 2020 16:46:15 -0700 Subject: [PATCH 016/101] More separation between git step examples and args The formatting of https://jenkins.io/doc/pipeline/steps/git/ drops the hard returns ( '
' ) that are used to separate the examples from the arguments. The hard returns are not dropped from the version of the git step help visible inside Jenkins at: http://jenkins-url/pipeline-syntax/html#git-step-with-git-and-polling As a compromise, place bold text 'Argument Descriptions' immediately after the last example. Ends the examples and makes the online generated version at https://jenkins.io/doc/pipeline/steps/git/ a little easier to read. The change to https://jenkins.io/doc/pipeline/steps/git/ won't be visible until the official release of the git plugin includes this commit. That will be a release *after* git plugin 4.1.0. This change is *not* included in git plugin 4.1.0. --- src/main/resources/jenkins/plugins/git/GitStep/help.html | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/src/main/resources/jenkins/plugins/git/GitStep/help.html b/src/main/resources/jenkins/plugins/git/GitStep/help.html index aad0094689..df9633e416 100644 --- a/src/main/resources/jenkins/plugins/git/GitStep/help.html +++ b/src/main/resources/jenkins/plugins/git/GitStep/help.html @@ -13,6 +13,7 @@
  • Git step with https and changelog disabled
  • Git step with git protocol and polling disabled
  • + See the argument descriptions for more details.

    @@ -114,4 +115,11 @@

    +
    + + Argument Descriptions + + + + From 034b8ebadaee290be5289c2d783c267779ea13f8 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Mon, 20 Jan 2020 19:17:30 -0700 Subject: [PATCH 017/101] [maven-release-plugin] prepare release git-4.1.1 --- pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index 3fa1c149cd..d4f6f31580 100644 --- a/pom.xml +++ b/pom.xml @@ -17,7 +17,7 @@ git - ${revision}${changelist} + 4.1.1 hpi Jenkins Git plugin Integrates Jenkins with GIT SCM @@ -272,7 +272,7 @@ scm:git:git://github.com/jenkinsci/${project.artifactId}-plugin.git scm:git:git@github.com:jenkinsci/${project.artifactId}-plugin.git https://github.com/jenkinsci/${project.artifactId}-plugin - ${scmTag} + git-4.1.1 From 2dcee862588f97301fc66e28d0cbbb000d833283 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Mon, 20 Jan 2020 19:17:39 -0700 Subject: [PATCH 018/101] [maven-release-plugin] prepare for next development iteration --- pom.xml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/pom.xml b/pom.xml index d4f6f31580..c55854d566 100644 --- a/pom.xml +++ b/pom.xml @@ -17,7 +17,7 @@ git - 4.1.1 + ${revision}${changelist} hpi Jenkins Git plugin Integrates Jenkins with GIT SCM @@ -25,7 +25,7 @@ 2007 - 4.1.1 + 4.1.2 -SNAPSHOT 2.138.4 8 @@ -272,7 +272,7 @@ scm:git:git://github.com/jenkinsci/${project.artifactId}-plugin.git scm:git:git@github.com:jenkinsci/${project.artifactId}-plugin.git https://github.com/jenkinsci/${project.artifactId}-plugin - git-4.1.1 + ${scmTag} From c0dfa85e1da219a6e3d36942b8b9a5579c83b4d6 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Tue, 21 Jan 2020 07:26:21 -0700 Subject: [PATCH 019/101] Use docs from tagged release Don't use the docs file from the master branch, since it usually contains unreleased content. --- pom.xml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index c55854d566..c79e7696b2 100644 --- a/pom.xml +++ b/pom.xml @@ -21,7 +21,8 @@ hpi Jenkins Git plugin Integrates Jenkins with GIT SCM - https://github.com/jenkinsci/git-plugin/blob/master/README.adoc + + https://github.com/jenkinsci/${project.artifactId}-plugin/tree/${project.artifactId}-${revision}/README.adoc 2007 From cb21ea12bb5eb5b003e807dab537572ef2cc9d81 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Tue, 21 Jan 2020 07:26:50 -0700 Subject: [PATCH 020/101] Fix capitalizastion of git in description --- pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index c79e7696b2..5f2b8132e7 100644 --- a/pom.xml +++ b/pom.xml @@ -20,7 +20,7 @@ ${revision}${changelist} hpi Jenkins Git plugin - Integrates Jenkins with GIT SCM + Integrates Jenkins with Git SCM https://github.com/jenkinsci/${project.artifactId}-plugin/tree/${project.artifactId}-${revision}/README.adoc 2007 From 2394fc88cfd6bb7ed48ca78a3b45a1943c681243 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Wed, 22 Jan 2020 00:33:14 +0530 Subject: [PATCH 021/101] =Fixing the Null exception in GIT_URL_n by adding a null check --- src/main/java/hudson/plugins/git/GitSCM.java | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/main/java/hudson/plugins/git/GitSCM.java b/src/main/java/hudson/plugins/git/GitSCM.java index 9aa053790b..cda79c5386 100644 --- a/src/main/java/hudson/plugins/git/GitSCM.java +++ b/src/main/java/hudson/plugins/git/GitSCM.java @@ -1382,8 +1382,10 @@ public void buildEnvironment(Run build, java.util.Map env) } else { int count=1; for(UserRemoteConfig config:userRemoteConfigs) { - env.put("GIT_URL_"+count, config.getUrl()); - count++; + if(config.getUrl()!=null){ + env.put("GIT_URL_"+count, config.getUrl()); + count++; + } } } From 131dc9fc53330282167d915e487e48b6dd613a1b Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Wed, 22 Jan 2020 00:52:20 +0530 Subject: [PATCH 022/101] =Added a unit test to show the bug and its fix --- .../java/hudson/plugins/git/GitSCMTest.java | 20 +++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/src/test/java/hudson/plugins/git/GitSCMTest.java b/src/test/java/hudson/plugins/git/GitSCMTest.java index df5e9c16df..5eeaa86041 100644 --- a/src/test/java/hudson/plugins/git/GitSCMTest.java +++ b/src/test/java/hudson/plugins/git/GitSCMTest.java @@ -312,6 +312,26 @@ public void testSpecificRefspecsWithoutCloneOption() throws Exception { build(projectWithMaster, Result.SUCCESS); /* If clone refspec had been honored, this would fail */ build(projectWithFoo, Result.SUCCESS, commitFile1); } + + /** + * This test confirm the behaviour of not allowing null values as environment variables and hence has been fixed + * with a null check. If the second repo is added accidentally but not filled in the text field, the build won't fail. + * @throws Exception on error + */ + @Test + @Issue("JENKINS-38608") + public void testAddSecondRepositoryWithNULLValue() throws Exception{ + String repoURL = "https://github.com/jenkinsci/git-plugin"; + List repos = new ArrayList<>(); + repos.add(new UserRemoteConfig(repoURL, null, null, null)); + repos.add(new UserRemoteConfig(null, null, null, null)); + FreeStyleProject project = setupProject(repos, Collections.singletonList(new BranchSpec("master")), null, false, null); + EnvVars vars = project.getCharacteristicEnvVars(); + FreeStyleBuild build = build(project, Result.SUCCESS); + GitSCM scm = (GitSCM) project.getScm(); + scm.getExtensions().add(new LocalBranch("master")); + scm.buildEnvironment(build, vars); + } @Test public void testBranchSpecWithRemotesHierarchical() throws Exception { From 6181977afa104d97ef5041aa3524a97042068f61 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Wed, 22 Jan 2020 02:33:38 +0530 Subject: [PATCH 023/101] =Corrected the indentation in GitSCM.java --- src/main/java/hudson/plugins/git/GitSCM.java | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/main/java/hudson/plugins/git/GitSCM.java b/src/main/java/hudson/plugins/git/GitSCM.java index cda79c5386..0026d6cfd5 100644 --- a/src/main/java/hudson/plugins/git/GitSCM.java +++ b/src/main/java/hudson/plugins/git/GitSCM.java @@ -1382,10 +1382,10 @@ public void buildEnvironment(Run build, java.util.Map env) } else { int count=1; for(UserRemoteConfig config:userRemoteConfigs) { - if(config.getUrl()!=null){ - env.put("GIT_URL_"+count, config.getUrl()); - count++; - } + if(config.getUrl()!=null) { + env.put("GIT_URL_" + count, config.getUrl()); + count++; + } } } From 7ab3fa670faac539f07d60667403b26b121d989a Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Thu, 23 Jan 2020 00:21:28 +0530 Subject: [PATCH 024/101] =[JENKINS-38608] reporting a better message to the user for empty repo URL --- src/main/java/hudson/plugins/git/GitSCM.java | 18 ++++++-- .../java/hudson/plugins/git/GitSCMTest.java | 46 +++++++++++++++---- 2 files changed, 49 insertions(+), 15 deletions(-) diff --git a/src/main/java/hudson/plugins/git/GitSCM.java b/src/main/java/hudson/plugins/git/GitSCM.java index 0026d6cfd5..5a67b5436f 100644 --- a/src/main/java/hudson/plugins/git/GitSCM.java +++ b/src/main/java/hudson/plugins/git/GitSCM.java @@ -1376,16 +1376,24 @@ public void buildEnvironment(Run build, java.util.Map env) } } + /* Check all repository URLs are not empty */ + /* JENKINS-38608 reports an unhelpful error message when a repository URL is empty */ + /* Throws an IllegalArgumentException because that exception is thrown by env.put() on a null argument */ + int repoCount = 1; + for (UserRemoteConfig config:userRemoteConfigs) { + if (config.getUrl() == null) { + throw new IllegalArgumentException("Git repository URL " + repoCount + " is an empty string in job definition. Checkout requires a valid repository URL"); + } + repoCount++; + } if (userRemoteConfigs.size()==1){ env.put("GIT_URL", userRemoteConfigs.get(0).getUrl()); } else { int count=1; - for(UserRemoteConfig config:userRemoteConfigs) { - if(config.getUrl()!=null) { - env.put("GIT_URL_" + count, config.getUrl()); - count++; - } + for (UserRemoteConfig config:userRemoteConfigs) { + env.put("GIT_URL_" + count, config.getUrl()); + count++; } } diff --git a/src/test/java/hudson/plugins/git/GitSCMTest.java b/src/test/java/hudson/plugins/git/GitSCMTest.java index 5eeaa86041..c81dd8b317 100644 --- a/src/test/java/hudson/plugins/git/GitSCMTest.java +++ b/src/test/java/hudson/plugins/git/GitSCMTest.java @@ -312,25 +312,51 @@ public void testSpecificRefspecsWithoutCloneOption() throws Exception { build(projectWithMaster, Result.SUCCESS); /* If clone refspec had been honored, this would fail */ build(projectWithFoo, Result.SUCCESS, commitFile1); } - + /** - * This test confirm the behaviour of not allowing null values as environment variables and hence has been fixed - * with a null check. If the second repo is added accidentally but not filled in the text field, the build won't fail. + * An empty remote repo URL failed the job as expected but provided + * a poor diagnostic message. The fix for JENKINS-38608 improves + * the error message to be clear and helpful. This test checks for + * that error message. * @throws Exception on error */ @Test @Issue("JENKINS-38608") - public void testAddSecondRepositoryWithNULLValue() throws Exception{ - String repoURL = "https://github.com/jenkinsci/git-plugin"; + public void testAddFirstRepositoryWithNullRepoURL() throws Exception{ + List repos = new ArrayList<>(); + repos.add(new UserRemoteConfig(null, null, null, null)); + FreeStyleProject project = setupProject(repos, Collections.singletonList(new BranchSpec("master")), null, false, null); + FreeStyleBuild build = build(project, Result.FAILURE); + // Before JENKINS-38608 fix + assertFalse("Build log reports 'Null value not allowed'", + build.getLog().contains("Null value not allowed as an environment variable: GIT_URL")); + // After JENKINS-38608 fix + assertTrue("Build log did not report empty string in job definition", + build.getLog().contains("Git repository URL 1 is an empty string in job definition. Checkout requires a valid repository URL")); + } + + /** + * An empty remote repo URL failed the job as expected but provided + * a poor diagnostic message. The fix for JENKINS-38608 improves + * the error message to be clear and helpful. This test checks for + * that error message when the second URL is empty. + * @throws Exception on error + */ + @Test + @Issue("JENKINS-38608") + public void testAddSecondRepositoryWithNullRepoURL() throws Exception{ + String repoURL = "https://example.com/non-empty/repo/url"; List repos = new ArrayList<>(); repos.add(new UserRemoteConfig(repoURL, null, null, null)); repos.add(new UserRemoteConfig(null, null, null, null)); FreeStyleProject project = setupProject(repos, Collections.singletonList(new BranchSpec("master")), null, false, null); - EnvVars vars = project.getCharacteristicEnvVars(); - FreeStyleBuild build = build(project, Result.SUCCESS); - GitSCM scm = (GitSCM) project.getScm(); - scm.getExtensions().add(new LocalBranch("master")); - scm.buildEnvironment(build, vars); + FreeStyleBuild build = build(project, Result.FAILURE); + // Before JENKINS-38608 fix + assertFalse("Build log reports 'Null value not allowed'", + build.getLog().contains("Null value not allowed as an environment variable: GIT_URL_2")); + // After JENKINS-38608 fix + assertTrue("Build log did not report empty string in job definition for URL 2", + build.getLog().contains("Git repository URL 2 is an empty string in job definition. Checkout requires a valid repository URL")); } @Test From 335efe962ad7c5c623106246ddab9ab887f4d81a Mon Sep 17 00:00:00 2001 From: rishabhBudhouliya <31189405+rishabhBudhouliya@users.noreply.github.com> Date: Thu, 23 Jan 2020 01:34:38 +0530 Subject: [PATCH 025/101] Change in indentation --- src/main/java/hudson/plugins/git/GitSCM.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/hudson/plugins/git/GitSCM.java b/src/main/java/hudson/plugins/git/GitSCM.java index 5a67b5436f..6d56980a6e 100644 --- a/src/main/java/hudson/plugins/git/GitSCM.java +++ b/src/main/java/hudson/plugins/git/GitSCM.java @@ -1391,7 +1391,7 @@ public void buildEnvironment(Run build, java.util.Map env) env.put("GIT_URL", userRemoteConfigs.get(0).getUrl()); } else { int count=1; - for (UserRemoteConfig config:userRemoteConfigs) { + for(UserRemoteConfig config:userRemoteConfigs) { env.put("GIT_URL_" + count, config.getUrl()); count++; } From 57fe348e49a5ac506a528f00d8c134c31026e644 Mon Sep 17 00:00:00 2001 From: rishabhBudhouliya <31189405+rishabhBudhouliya@users.noreply.github.com> Date: Thu, 23 Jan 2020 01:35:53 +0530 Subject: [PATCH 026/101] Change in indentation --- src/main/java/hudson/plugins/git/GitSCM.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/hudson/plugins/git/GitSCM.java b/src/main/java/hudson/plugins/git/GitSCM.java index 6d56980a6e..1334574c53 100644 --- a/src/main/java/hudson/plugins/git/GitSCM.java +++ b/src/main/java/hudson/plugins/git/GitSCM.java @@ -1392,7 +1392,7 @@ public void buildEnvironment(Run build, java.util.Map env) } else { int count=1; for(UserRemoteConfig config:userRemoteConfigs) { - env.put("GIT_URL_" + count, config.getUrl()); + env.put("GIT_URL_"+count, config.getUrl()); count++; } } From ae6259ae6b7727da60f887bccd54f87304a34eb9 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Sun, 26 Jan 2020 18:54:33 +0530 Subject: [PATCH 027/101] =[JENKINS-57660] Addition of a doCheck validation method for refSpec with unit test --- .../hudson/plugins/git/UserRemoteConfig.java | 42 +++++++++++++++++++ .../git/UserRemoteConfigRefSpecTest.java | 21 ++++++++++ 2 files changed, 63 insertions(+) create mode 100644 src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java diff --git a/src/main/java/hudson/plugins/git/UserRemoteConfig.java b/src/main/java/hudson/plugins/git/UserRemoteConfig.java index 72abac2a0c..b50662d1f3 100644 --- a/src/main/java/hudson/plugins/git/UserRemoteConfig.java +++ b/src/main/java/hudson/plugins/git/UserRemoteConfig.java @@ -21,6 +21,8 @@ import hudson.util.FormValidation; import hudson.util.ListBoxModel; import jenkins.model.Jenkins; +import org.eclipse.jgit.lib.Config; +import org.eclipse.jgit.transport.RemoteConfig; import org.jenkinsci.plugins.gitclient.Git; import org.jenkinsci.plugins.gitclient.GitClient; import org.jenkinsci.plugins.gitclient.GitURIRequirementsBuilder; @@ -32,6 +34,7 @@ import java.io.IOException; import java.io.Serializable; +import java.util.List; import java.util.regex.Pattern; import java.util.UUID; import org.apache.commons.lang.StringUtils; @@ -212,6 +215,45 @@ public FormValidation doCheckUrl(@AncestorInPath Item item, return FormValidation.ok(); } + /** + * A form validation logic as a method to check the specification of 'refSpec' and notify the user about + * illegal specs before applying the project configuration + * @param name Name of the remote repository + * @param url Repository URL + * @param value value of RefSpec + * @return FormValidation.ok() or FormValidation.error() + * @throws IllegalArgumentException + */ + public FormValidation doCheckRefspec(@QueryParameter String name, + @QueryParameter String url, + @QueryParameter String value) throws IllegalArgumentException { + + String refSpec = Util.fixEmptyAndTrim(value); + + if(refSpec==null){ + return FormValidation.error(Messages.UserRemoteConfig_CheckUrl_UrlIsNull()); + } + + if(refSpec.contains("$")){ + // set by variable, can't validate + return FormValidation.ok(); + } + + Config repoConfig = new Config(); + + repoConfig.setString("remote", name, "url", url); + repoConfig.setString("remote", name, "fetch", refSpec); + + //Attempt to fetch remote repositories using the repoConfig + try { + RemoteConfig.getAllRemoteConfigs(repoConfig); + } catch (Exception e) { + return FormValidation.error("Specification is wrong"); + } + + return FormValidation.ok(); + } + private static StandardCredentials lookupCredentials(@CheckForNull Item project, String credentialId, String uri) { return (credentialId == null) ? null : CredentialsMatchers.firstOrNull( CredentialsProvider.lookupCredentials(StandardCredentials.class, project, ACL.SYSTEM, diff --git a/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java b/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java new file mode 100644 index 0000000000..e9657337b6 --- /dev/null +++ b/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java @@ -0,0 +1,21 @@ +package hudson.plugins.git; + +import hudson.util.FormValidation; +import org.junit.Test; +import org.jvnet.hudson.test.Issue; + +import static org.junit.Assert.assertEquals; + + +public class UserRemoteConfigRefSpecTest { + + @Issue("JENKINS-57660") + @Test + public void testdoCheckRefspec(){ + String url = "https://github.com/daytonpa/pipeline_test_example.git"; + String name = "origin"; + String refSpec = "refs/heads/master"; + UserRemoteConfig.DescriptorImpl descriptor = new UserRemoteConfig.DescriptorImpl(); + assertEquals(FormValidation.ok(), descriptor.doCheckRefspec(url, name, refSpec)); + } +} From d65fd746e90a76c2532c47a1f75fd79e93a0abec Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Sun, 26 Jan 2020 18:59:08 +0530 Subject: [PATCH 028/101] =change in response in FormValidation --- src/main/java/hudson/plugins/git/UserRemoteConfig.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/hudson/plugins/git/UserRemoteConfig.java b/src/main/java/hudson/plugins/git/UserRemoteConfig.java index b50662d1f3..4b4cbaa329 100644 --- a/src/main/java/hudson/plugins/git/UserRemoteConfig.java +++ b/src/main/java/hudson/plugins/git/UserRemoteConfig.java @@ -248,7 +248,7 @@ public FormValidation doCheckRefspec(@QueryParameter String name, try { RemoteConfig.getAllRemoteConfigs(repoConfig); } catch (Exception e) { - return FormValidation.error("Specification is wrong"); + return FormValidation.error("Specification is invalid"); } return FormValidation.ok(); From 814a8763ac932da7cd37a98f2bc4bcf6694b6aef Mon Sep 17 00:00:00 2001 From: rishabhBudhouliya <31189405+rishabhBudhouliya@users.noreply.github.com> Date: Sun, 26 Jan 2020 21:35:37 +0530 Subject: [PATCH 029/101] Update src/main/java/hudson/plugins/git/UserRemoteConfig.java with correct indentation Co-Authored-By: Raihaan Shouhell --- src/main/java/hudson/plugins/git/UserRemoteConfig.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/hudson/plugins/git/UserRemoteConfig.java b/src/main/java/hudson/plugins/git/UserRemoteConfig.java index 4b4cbaa329..b00088393f 100644 --- a/src/main/java/hudson/plugins/git/UserRemoteConfig.java +++ b/src/main/java/hudson/plugins/git/UserRemoteConfig.java @@ -230,7 +230,7 @@ public FormValidation doCheckRefspec(@QueryParameter String name, String refSpec = Util.fixEmptyAndTrim(value); - if(refSpec==null){ + if(refSpec == null){ return FormValidation.error(Messages.UserRemoteConfig_CheckUrl_UrlIsNull()); } From 142768d4c2d17fbe736f88c1493148db45ba4a67 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Mon, 27 Jan 2020 00:09:11 +0530 Subject: [PATCH 030/101] =Added more test cases and localized message --- .../hudson/plugins/git/UserRemoteConfig.java | 5 +- .../hudson/plugins/git/Messages.properties | 2 + .../git/UserRemoteConfigRefSpecTest.java | 78 ++++++++++++++++++- 3 files changed, 78 insertions(+), 7 deletions(-) diff --git a/src/main/java/hudson/plugins/git/UserRemoteConfig.java b/src/main/java/hudson/plugins/git/UserRemoteConfig.java index 4b4cbaa329..7139fe41e9 100644 --- a/src/main/java/hudson/plugins/git/UserRemoteConfig.java +++ b/src/main/java/hudson/plugins/git/UserRemoteConfig.java @@ -34,7 +34,6 @@ import java.io.IOException; import java.io.Serializable; -import java.util.List; import java.util.regex.Pattern; import java.util.UUID; import org.apache.commons.lang.StringUtils; @@ -231,7 +230,7 @@ public FormValidation doCheckRefspec(@QueryParameter String name, String refSpec = Util.fixEmptyAndTrim(value); if(refSpec==null){ - return FormValidation.error(Messages.UserRemoteConfig_CheckUrl_UrlIsNull()); + return FormValidation.error(Messages.UserRemoteConfig_CheckRefSpec_RefSpecIsNull()); } if(refSpec.contains("$")){ @@ -248,7 +247,7 @@ public FormValidation doCheckRefspec(@QueryParameter String name, try { RemoteConfig.getAllRemoteConfigs(repoConfig); } catch (Exception e) { - return FormValidation.error("Specification is invalid"); + return FormValidation.error(Messages.UserRemoteConfig_CheckRefSpec_InvalidRefSpec()); } return FormValidation.ok(); diff --git a/src/main/resources/hudson/plugins/git/Messages.properties b/src/main/resources/hudson/plugins/git/Messages.properties index ba1cf8ee0c..a9d73ba2b3 100644 --- a/src/main/resources/hudson/plugins/git/Messages.properties +++ b/src/main/resources/hudson/plugins/git/Messages.properties @@ -5,6 +5,8 @@ BuildChooser_Ancestry=Ancestry BuildChooser_BuildingLastRevision=No new revisions were found; the most-recently built branch will be built again. UserRemoteConfig.FailedToConnect=Failed to connect to repository : {0} UserRemoteConfig.CheckUrl.UrlIsNull=Please enter Git repository. +UserRemoteConfig.CheckRefSpec.RefSpecIsNull=Please enter valid RefSpec. +UserRemoteConfig.CheckRefSpec.InvalidRefSpec=Specification is invalid. GitPublisher.Check.TagName=Tag Name GitPublisher.Check.BranchName=Branch Name diff --git a/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java b/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java index e9657337b6..93a8066aae 100644 --- a/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java +++ b/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java @@ -4,6 +4,9 @@ import org.junit.Test; import org.jvnet.hudson.test.Issue; +import java.util.ArrayList; +import java.util.List; + import static org.junit.Assert.assertEquals; @@ -11,11 +14,78 @@ public class UserRemoteConfigRefSpecTest { @Issue("JENKINS-57660") @Test - public void testdoCheckRefspec(){ - String url = "https://github.com/daytonpa/pipeline_test_example.git"; + public void testdoCheckRefspecSuccessWithoutWildcards(){ + String url = "git://git.example.com/repository-that-does-not-exist"; + String name = "origin"; + List refSpec = new ArrayList<>(); + refSpec.add("+refs/heads/master:refs/remotes/origin/master"); + refSpec.add("+refs/heads/JENKINS-57660:refs/remotes/origin/JENKINS-57660"); + refSpec.add("master:refs/remotes/origin/mymaster"); + refSpec.add("master:refs/remotes/origin/mymaster topic:refs/remotes/origin/topic"); + + UserRemoteConfig.DescriptorImpl descriptor = new UserRemoteConfig.DescriptorImpl(); + for (String ref:refSpec) { + assertEquals(FormValidation.ok(), descriptor.doCheckRefspec(url, name, ref)); + } + } + + @Issue("JENKINS-57660") + @Test + public void testdoCheckRefspecSuccessWithMatchedWildCards(){ + String url = "git://git.example.com/repository-that-does-not-exist"; + String name = "origin"; + List refSpec = new ArrayList<>(); + refSpec.add("+refs/heads/qa/*:refs/remotes/origin/qa/*"); + refSpec.add("+refs/pull/*/head:refs/remotes/origin/pr/*"); + + UserRemoteConfig.DescriptorImpl descriptor = new UserRemoteConfig.DescriptorImpl(); + for (String ref:refSpec) { + assertEquals(FormValidation.ok(), descriptor.doCheckRefspec(url, name, ref)); + } + } + + @Issue("JENKINS-57660") + @Test + public void testdoCheckRefspecFailureWithUnMatchedWildCards(){ + String url = "git://git.example.com/repository-that-does-not-exist"; + String name = "origin"; + List refSpec = new ArrayList<>(); + refSpec.add("+refs/heads/qa:refs/remotes/origin/qa/*"); + refSpec.add("+refs/heads/qa/*:refs/remotes/origin/qa"); + + UserRemoteConfig.DescriptorImpl descriptor = new UserRemoteConfig.DescriptorImpl(); + for (String ref:refSpec) { + assertEquals("Specification is invalid.", + descriptor.doCheckRefspec(url, name, ref).getLocalizedMessage()); + } + } + + @Issue("JENKINS-57660") + @Test + public void testdoCheckRefspecFailureWithEmptyString(){ + String url = "git://git.example.com/repository-that-does-not-exist"; + String name = "origin"; + List refSpec = new ArrayList<>(); + refSpec.add(""); + + UserRemoteConfig.DescriptorImpl descriptor = new UserRemoteConfig.DescriptorImpl(); + for (String ref:refSpec) { + assertEquals("Please enter valid RefSpec.", + descriptor.doCheckRefspec(url, name, ref).getLocalizedMessage()); + } + } + + @Issue("JENKINS-57660") + @Test + public void testdoCheckRefspecSuccessWithPartialGlobs(){ + String url = "git://git.example.com/repository-that-does-not-exist"; String name = "origin"; - String refSpec = "refs/heads/master"; + List refSpec = new ArrayList<>(); + refSpec.add("+refs/heads/qa*:refs/remotes/origin/qa*"); UserRemoteConfig.DescriptorImpl descriptor = new UserRemoteConfig.DescriptorImpl(); - assertEquals(FormValidation.ok(), descriptor.doCheckRefspec(url, name, refSpec)); + for (String ref:refSpec) { + assertEquals(FormValidation.ok(), + descriptor.doCheckRefspec(url, name, ref)); + } } } From 50530b9138b7f7820583c984400a907a43e0907f Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Mon, 27 Jan 2020 13:13:32 +0530 Subject: [PATCH 031/101] =Fix to accept empty refspec and the test associated with it --- src/main/java/hudson/plugins/git/UserRemoteConfig.java | 3 ++- src/main/resources/hudson/plugins/git/Messages.properties | 1 - .../hudson/plugins/git/UserRemoteConfigRefSpecTest.java | 6 +++--- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/src/main/java/hudson/plugins/git/UserRemoteConfig.java b/src/main/java/hudson/plugins/git/UserRemoteConfig.java index 40ad89f202..bbbd27f8d9 100644 --- a/src/main/java/hudson/plugins/git/UserRemoteConfig.java +++ b/src/main/java/hudson/plugins/git/UserRemoteConfig.java @@ -230,7 +230,8 @@ public FormValidation doCheckRefspec(@QueryParameter String name, String refSpec = Util.fixEmptyAndTrim(value); if(refSpec == null){ - return FormValidation.error(Messages.UserRemoteConfig_CheckUrl_UrlIsNull()); + // We fix empty field value with a default refspec, hence we send ok. + return FormValidation.ok(); } if(refSpec.contains("$")){ diff --git a/src/main/resources/hudson/plugins/git/Messages.properties b/src/main/resources/hudson/plugins/git/Messages.properties index a9d73ba2b3..11401f4bd1 100644 --- a/src/main/resources/hudson/plugins/git/Messages.properties +++ b/src/main/resources/hudson/plugins/git/Messages.properties @@ -5,7 +5,6 @@ BuildChooser_Ancestry=Ancestry BuildChooser_BuildingLastRevision=No new revisions were found; the most-recently built branch will be built again. UserRemoteConfig.FailedToConnect=Failed to connect to repository : {0} UserRemoteConfig.CheckUrl.UrlIsNull=Please enter Git repository. -UserRemoteConfig.CheckRefSpec.RefSpecIsNull=Please enter valid RefSpec. UserRemoteConfig.CheckRefSpec.InvalidRefSpec=Specification is invalid. GitPublisher.Check.TagName=Tag Name diff --git a/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java b/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java index 93a8066aae..1eb04dafc7 100644 --- a/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java +++ b/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java @@ -62,7 +62,7 @@ public void testdoCheckRefspecFailureWithUnMatchedWildCards(){ @Issue("JENKINS-57660") @Test - public void testdoCheckRefspecFailureWithEmptyString(){ + public void testdoCheckRefspecSuccessWithEmptyString(){ String url = "git://git.example.com/repository-that-does-not-exist"; String name = "origin"; List refSpec = new ArrayList<>(); @@ -70,8 +70,8 @@ public void testdoCheckRefspecFailureWithEmptyString(){ UserRemoteConfig.DescriptorImpl descriptor = new UserRemoteConfig.DescriptorImpl(); for (String ref:refSpec) { - assertEquals("Please enter valid RefSpec.", - descriptor.doCheckRefspec(url, name, ref).getLocalizedMessage()); + assertEquals(FormValidation.ok(), + descriptor.doCheckRefspec(url, name, ref)); } } From 0ebb41ca9a00258b45d599cb3a6b745947a01472 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Mon, 27 Jan 2020 16:52:51 +0530 Subject: [PATCH 032/101] =Added another test case for environment variable --- .../plugins/git/UserRemoteConfigRefSpecTest.java | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java b/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java index 1eb04dafc7..d96eb41ef1 100644 --- a/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java +++ b/src/test/java/hudson/plugins/git/UserRemoteConfigRefSpecTest.java @@ -88,4 +88,18 @@ public void testdoCheckRefspecSuccessWithPartialGlobs(){ descriptor.doCheckRefspec(url, name, ref)); } } + + @Issue("JENKINS-57660") + @Test + public void testdoCheckRefspecSuccessWithEnvironmentVariable(){ + String url = "git://git.example.com/repository-that-does-not-exist"; + String name = "origin"; + List refSpec = new ArrayList<>(); + refSpec.add("$REFSPEC"); + UserRemoteConfig.DescriptorImpl descriptor = new UserRemoteConfig.DescriptorImpl(); + for (String ref:refSpec) { + assertEquals(FormValidation.ok(), + descriptor.doCheckRefspec(url, name, ref)); + } + } } From 2510bd3797b2379dd679f033a94cc556abd96ddc Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 31 Jan 2020 01:54:20 +0530 Subject: [PATCH 033/101] =[JENKINS-56063] added expansion of env variables in refspec in case of honor refspec --- .../plugins/git/extensions/impl/CloneOption.java | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java b/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java index be46f4339b..ffd3036965 100644 --- a/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java +++ b/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java @@ -14,6 +14,7 @@ import hudson.plugins.git.util.GitUtils; import hudson.slaves.NodeProperty; import java.io.IOException; +import java.util.ArrayList; import java.util.List; import java.util.Objects; import org.eclipse.jgit.transport.RefSpec; @@ -148,7 +149,20 @@ public void decorateCloneCommand(GitSCM scm, Run build, GitClient git, Tas // in a single job definition. RemoteConfig rc = scm.getRepositories().get(0); List refspecs = rc.getFetchRefSpecs(); - cmd.refspecs(refspecs); + List expandedrefSpecs = new ArrayList<>(); + Boolean check = false; + for (RefSpec ref:refspecs) { + if(ref.toString().contains("$")){ + EnvVars env = build.getEnvironment(listener); + expandedrefSpecs.add(new RefSpec(env.expand(ref.toString()))); + check = true; + } + } + if(!check) { + cmd.refspecs(refspecs); + } else{ + cmd.refspecs(expandedrefSpecs); + } } cmd.timeout(timeout); From 7d7f67057c8c79c050d8fcab00535e091deec978 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 31 Jan 2020 12:55:51 +0530 Subject: [PATCH 034/101] =removed the check flag and changed the implementation --- .../plugins/git/extensions/impl/CloneOption.java | 16 ++++------------ 1 file changed, 4 insertions(+), 12 deletions(-) diff --git a/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java b/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java index ffd3036965..eda5fa9785 100644 --- a/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java +++ b/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java @@ -149,20 +149,12 @@ public void decorateCloneCommand(GitSCM scm, Run build, GitClient git, Tas // in a single job definition. RemoteConfig rc = scm.getRepositories().get(0); List refspecs = rc.getFetchRefSpecs(); - List expandedrefSpecs = new ArrayList<>(); - Boolean check = false; + List expandedRefSpecs = new ArrayList<>(); + EnvVars env = build.getEnvironment(listener); for (RefSpec ref:refspecs) { - if(ref.toString().contains("$")){ - EnvVars env = build.getEnvironment(listener); - expandedrefSpecs.add(new RefSpec(env.expand(ref.toString()))); - check = true; - } - } - if(!check) { - cmd.refspecs(refspecs); - } else{ - cmd.refspecs(expandedrefSpecs); + expandedRefSpecs.add(new RefSpec(env.expand(ref.toString()))); } + cmd.refspecs(expandedRefSpecs); } cmd.timeout(timeout); From 58320c4ee6a1db6b432c09511fcfa67c78889560 Mon Sep 17 00:00:00 2001 From: rishabhBudhouliya <31189405+rishabhBudhouliya@users.noreply.github.com> Date: Sat, 1 Feb 2020 12:28:40 +0530 Subject: [PATCH 035/101] Changed minor indentation issues --- .../java/hudson/plugins/git/extensions/impl/CloneOption.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java b/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java index eda5fa9785..fb1bdf6933 100644 --- a/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java +++ b/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java @@ -151,10 +151,10 @@ public void decorateCloneCommand(GitSCM scm, Run build, GitClient git, Tas List refspecs = rc.getFetchRefSpecs(); List expandedRefSpecs = new ArrayList<>(); EnvVars env = build.getEnvironment(listener); - for (RefSpec ref:refspecs) { + for (RefSpec ref : refspecs) { expandedRefSpecs.add(new RefSpec(env.expand(ref.toString()))); } - cmd.refspecs(expandedRefSpecs); + cmd.refspecs(expandedRefSpecs); } cmd.timeout(timeout); From 720509e95c75466b462bb257ef402860619d19c1 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 3 Feb 2020 08:27:59 +0000 Subject: [PATCH 036/101] Bump equalsverifier from 3.1.11 to 3.1.12 Bumps [equalsverifier](https://github.com/jqno/equalsverifier) from 3.1.11 to 3.1.12. - [Release notes](https://github.com/jqno/equalsverifier/releases) - [Changelog](https://github.com/jqno/equalsverifier/blob/master/CHANGELOG.md) - [Commits](https://github.com/jqno/equalsverifier/compare/equalsverifier-3.1.11...equalsverifier-3.1.12) Signed-off-by: dependabot-preview[bot] --- pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 5f2b8132e7..5302f476b3 100644 --- a/pom.xml +++ b/pom.xml @@ -140,7 +140,7 @@ nl.jqno.equalsverifier equalsverifier - 3.1.11 + 3.1.12 test From f1729de591f70f62f31ca0844f313fe4a45f4766 Mon Sep 17 00:00:00 2001 From: Sven Hickstein Date: Mon, 3 Jul 2017 09:04:35 +0200 Subject: [PATCH 037/101] Allow disabling of multi candidate scheduling Add an additional behaviour that disables the multi candidate scheduling. The default behaviour of the git plugin is to check for new changes and trigger a new build for every tip of every branch. When working with big repositories, high build times and many independent branches, this behaviour leads to an unnecessary high resource consumption. --- src/main/java/hudson/plugins/git/GitSCM.java | 24 ++++-- .../git/extensions/GitSCMExtension.java | 9 +++ .../impl/BuildSingleRevisionOnly.java | 30 +++++++ .../impl/BuildSingleRevisionOnly/help.html | 10 +++ .../impl/BuildSingleRevisionOnlyTest.java | 80 +++++++++++++++++++ 5 files changed, 145 insertions(+), 8 deletions(-) create mode 100644 src/main/java/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnly.java create mode 100644 src/main/resources/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnly/help.html create mode 100644 src/test/java/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnlyTest.java diff --git a/src/main/java/hudson/plugins/git/GitSCM.java b/src/main/java/hudson/plugins/git/GitSCM.java index 1334574c53..d81a96c593 100644 --- a/src/main/java/hudson/plugins/git/GitSCM.java +++ b/src/main/java/hudson/plugins/git/GitSCM.java @@ -33,6 +33,7 @@ import hudson.plugins.git.extensions.GitSCMExtensionDescriptor; import hudson.plugins.git.extensions.impl.AuthorInChangelog; import hudson.plugins.git.extensions.impl.BuildChooserSetting; +import hudson.plugins.git.extensions.impl.BuildSingleRevisionOnly; import hudson.plugins.git.extensions.impl.ChangelogToBranch; import hudson.plugins.git.extensions.impl.PathRestriction; import hudson.plugins.git.extensions.impl.LocalBranch; @@ -1067,17 +1068,24 @@ public EnvVars getEnvironment() { if (buildData.getBuildsByBranchName().size() >= 100) { log.println("JENKINS-19022: warning: possible memory leak due to Git plugin usage; see: https://wiki.jenkins.io/display/JENKINS/Remove+Git+Plugin+BuildsByBranch+BuildData"); } + boolean checkForMultipleRevisions = true; + BuildSingleRevisionOnly ext = extensions.get(BuildSingleRevisionOnly.class); + if (ext != null) { + checkForMultipleRevisions = ext.enableMultipleRevisionDetection(); + } if (candidates.size() > 1) { log.println("Multiple candidate revisions"); - Job job = build.getParent(); - if (job instanceof AbstractProject) { - AbstractProject project = (AbstractProject) job; - if (!project.isDisabled()) { - log.println("Scheduling another build to catch up with " + project.getFullDisplayName()); - if (!project.scheduleBuild(0, new SCMTrigger.SCMTriggerCause("This build was triggered by build " - + build.getNumber() + " because more than one build candidate was found."))) { - log.println("WARNING: multiple candidate revisions, but unable to schedule build of " + project.getFullDisplayName()); + if (checkForMultipleRevisions) { + Job job = build.getParent(); + if (job instanceof AbstractProject) { + AbstractProject project = (AbstractProject) job; + if (!project.isDisabled()) { + log.println("Scheduling another build to catch up with " + project.getFullDisplayName()); + if (!project.scheduleBuild(0, new SCMTrigger.SCMTriggerCause("This build was triggered by build " + + build.getNumber() + " because more than one build candidate was found."))) { + log.println("WARNING: multiple candidate revisions, but unable to schedule build of " + project.getFullDisplayName()); + } } } } diff --git a/src/main/java/hudson/plugins/git/extensions/GitSCMExtension.java b/src/main/java/hudson/plugins/git/extensions/GitSCMExtension.java index 64a52d28cb..3d36eaf461 100644 --- a/src/main/java/hudson/plugins/git/extensions/GitSCMExtension.java +++ b/src/main/java/hudson/plugins/git/extensions/GitSCMExtension.java @@ -352,6 +352,15 @@ public GitClientType getRequiredClient() { return GitClientType.ANY; } + /** + * + * @return true to disable the scheduling of another build to catch up + * when multiple revisions are detected + */ + public boolean enableMultipleRevisionDetection() { + return true; + } + @Override public GitSCMExtensionDescriptor getDescriptor() { return (GitSCMExtensionDescriptor) super.getDescriptor(); diff --git a/src/main/java/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnly.java b/src/main/java/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnly.java new file mode 100644 index 0000000000..113e00cca0 --- /dev/null +++ b/src/main/java/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnly.java @@ -0,0 +1,30 @@ +package hudson.plugins.git.extensions.impl; + +import hudson.Extension; +import hudson.plugins.git.extensions.GitSCMExtension; +import hudson.plugins.git.extensions.GitSCMExtensionDescriptor; +import org.kohsuke.stapler.DataBoundConstructor; + +/** + * Don't trigger another build to catch up + * + * @author Sven Hickstein + */ +public class BuildSingleRevisionOnly extends GitSCMExtension { + @DataBoundConstructor + public BuildSingleRevisionOnly() { + } + + @Override + public boolean enableMultipleRevisionDetection() { + return false; + } + + @Extension + public static class DescriptorImpl extends GitSCMExtensionDescriptor { + @Override + public String getDisplayName() { + return "Build single revision only"; + } + } +} diff --git a/src/main/resources/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnly/help.html b/src/main/resources/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnly/help.html new file mode 100644 index 0000000000..46dd732b02 --- /dev/null +++ b/src/main/resources/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnly/help.html @@ -0,0 +1,10 @@ +
    + Disable scheduling for multiple candidate revisions.
    + If we have 3 branches:
    + ----A--.---.--- B
    +          \-----C
    + jenkins would try to build (B) and (C).
    + This behaviour disables this and only builds one of them.
    + It is helpful to reduce the load of the Jenkins infrastructure when the + SCM system like Bitbucket or GitHub should decide what commits to build. +
    diff --git a/src/test/java/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnlyTest.java b/src/test/java/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnlyTest.java new file mode 100644 index 0000000000..50a601c050 --- /dev/null +++ b/src/test/java/hudson/plugins/git/extensions/impl/BuildSingleRevisionOnlyTest.java @@ -0,0 +1,80 @@ +package hudson.plugins.git.extensions.impl; + +import hudson.model.FreeStyleBuild; +import hudson.model.FreeStyleProject; +import hudson.model.Result; +import hudson.plugins.git.AbstractGitTestCase; +import hudson.plugins.git.BranchSpec; + +import hudson.plugins.git.GitSCM; +import org.junit.Assert; +import org.junit.Test; + +import java.util.ArrayList; +import java.util.List; + +public class BuildSingleRevisionOnlyTest extends AbstractGitTestCase { + + @Test + public void testSingleRevision() throws Exception { + // This is the additional behaviour + List branchSpec = new ArrayList<>(); + branchSpec.add(new BranchSpec("master")); + branchSpec.add(new BranchSpec("foo")); + branchSpec.add(new BranchSpec("bar")); + FreeStyleProject project = setupProject(branchSpec, false, "", + "","", + "", false, ""); + + ((GitSCM) project.getScm()).getExtensions().add(new BuildSingleRevisionOnly()); + final String commitFile = "commitFile1"; + // create the initial master commit + commit(commitFile, johnDoe, "Initial commit in master"); + + // create additional branches and commits + git.branch("foo"); + git.branch("bar"); + git.checkoutBranch("foo", "master"); + commit(commitFile, johnDoe, "Commit in foo"); + git.checkoutBranch("bar", "master"); + commit(commitFile, johnDoe, "Commit in bar"); + + final FreeStyleBuild build = build(project, Result.SUCCESS, commitFile); + + rule.assertBuildStatusSuccess(build); + boolean result = build.getLog(100).contains( + String.format("Scheduling another build to catch up with %s", project.getName())); + Assert.assertFalse(result); + } + + @Test + public void testMultiRevision() throws Exception { + // This is the old and now default behaviour + List branchSpec = new ArrayList<>(); + branchSpec.add(new BranchSpec("master")); + branchSpec.add(new BranchSpec("foo")); + branchSpec.add(new BranchSpec("bar")); + FreeStyleProject project = setupProject(branchSpec, false, "", + "","", + "", false, ""); + + final String commitFile = "commitFile1"; + // create the initial master commit + commit(commitFile, johnDoe, "Initial commit in master"); + + // create additional branches and commits + git.branch("foo"); + git.branch("bar"); + git.checkoutBranch("foo", "master"); + commit(commitFile, johnDoe, "Commit in foo"); + git.checkoutBranch("bar", "master"); + commit(commitFile, johnDoe, "Commit in bar"); + + final FreeStyleBuild build = build(project, Result.SUCCESS, commitFile); + + rule.assertBuildStatusSuccess(build); + boolean result = build.getLog(100).contains( + String.format("Scheduling another build to catch up with %s", project.getName())); + Assert.assertTrue(result); + } +} From 6275800c2f4e92f710b469925edfa0cf8e5f08f7 Mon Sep 17 00:00:00 2001 From: loghi Date: Mon, 3 Feb 2020 19:24:15 +0530 Subject: [PATCH 038/101] Some basic tests were made --- .../git/MergeWithGitSCMExtensionTest.java | 95 +++++++++++++++++++ 1 file changed, 95 insertions(+) create mode 100644 src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java diff --git a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java new file mode 100644 index 0000000000..7577d8b97b --- /dev/null +++ b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java @@ -0,0 +1,95 @@ +package jenkins.plugins.git; + +import hudson.model.FreeStyleBuild; +import hudson.model.FreeStyleProject; +import hudson.model.Result; +import hudson.plugins.git.*; +import hudson.plugins.git.extensions.GitSCMExtension; +import hudson.plugins.git.extensions.GitSCMExtensionTest; +import hudson.plugins.git.extensions.impl.LocalBranch; +import hudson.plugins.git.extensions.impl.PreBuildMerge; +import hudson.plugins.git.util.BuildData; +import junit.framework.TestCase; +import nl.jqno.equalsverifier.EqualsVerifier; +import org.eclipse.jgit.lib.Constants; +import org.jenkinsci.plugins.gitclient.MergeCommand; +import org.junit.Test; + +import java.io.*; +import java.util.ArrayList; +import java.util.Collections; +import java.util.List; + +import static org.junit.Assert.*; +import static org.junit.Assert.assertEquals; + +public class MergeWithGitSCMExtensionTest extends GitSCMExtensionTest { + + private FreeStyleProject project; + + private TestGitRepo repo; + private String baseName; + private String baseHash; + private String MASTER_FILE = "commitFileBase"; + + public void before() throws Exception { + repo = new TestGitRepo("repo", tmp.newFolder(), listener); + // make an initial commit to master and get hash + this.baseHash=repo.commit(MASTER_FILE, repo.johnDoe, "Initial Commit"); + // set the base name as HEAD + this.baseName=Constants.MASTER; + project = setupBasicProject(repo); + // create integration branch + repo.git.branch("integration"); + + } + @Test + public void testBasicMergeWithSCMExtension() throws Exception { + FreeStyleBuild baseBuild = build(project, Result.SUCCESS); + } + + @Test + public void testFailedMergeWithSCMExtension() throws Exception { + FreeStyleBuild firstBuild = build(project, Result.SUCCESS); + assertEquals(GitSCM.class, project.getScm().getClass()); + GitSCM gitSCM = (GitSCM)project.getScm(); + BuildData buildData = gitSCM.getBuildData(firstBuild); + assertNotNull("Build data not found", buildData); + assertEquals(firstBuild.getNumber(), buildData.lastBuild.getBuildNumber()); + Revision firstMarked = buildData.lastBuild.getMarked(); + Revision firstRevision = buildData.lastBuild.getRevision(); + assertNotNull(firstMarked); + assertNotNull(firstRevision); + + // delete integration branch successfully and commit successfully + repo.git.deleteBranch("integration"); + repo.git.checkoutBranch("integration", "master"); + this.baseName=Constants.HEAD; + this.baseHash = repo.git.revParse(baseName).name(); + repo.commit(MASTER_FILE, "new content on integration branch", repo.johnDoe, repo.johnDoe, "Commit success!"); + repo.git.checkout().ref("master").execute(); + + // as baseName and baseHash don't change in master branch, this commit should merge ! + assertFalse("SCM polling should not detect any more changes after build", project.poll(listener).hasChanges()); + String conflictSha1= repo.commit(MASTER_FILE, "new content ", repo.johnDoe, repo.johnDoe, "Commit success!"); + assertTrue("SCM polling should detect changes", project.poll(listener).hasChanges()); + + + FreeStyleBuild secondBuild = build(project, Result.SUCCESS); + assertEquals(secondBuild.getNumber(), gitSCM.getBuildData(secondBuild).lastBuild.getBuildNumber()); + // buildData should mark this as built + assertEquals(conflictSha1, gitSCM.getBuildData(secondBuild).lastBuild.getMarked().getSha1String()); + assertEquals(conflictSha1, gitSCM.getBuildData(secondBuild).lastBuild.getRevision().getSha1String()); + + // Check to see that build data is not corrupted (JENKINS-44037) + assertEquals(firstBuild.getNumber(), gitSCM.getBuildData(firstBuild).lastBuild.getBuildNumber()); + assertEquals(firstMarked, gitSCM.getBuildData(firstBuild).lastBuild.getMarked()); + assertEquals(firstRevision, gitSCM.getBuildData(firstBuild).lastBuild.getRevision()); + } + + @Override + protected GitSCMExtension getExtension() { + return new MergeWithGitSCMExtension(baseName,baseHash); + } + +} \ No newline at end of file From ac90fc94e934e107c95453d5032ad7c671e0f7d7 Mon Sep 17 00:00:00 2001 From: Loghi Date: Tue, 4 Feb 2020 12:30:54 +0530 Subject: [PATCH 039/101] Update src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java Co-Authored-By: Raihaan Shouhell --- .../jenkins/plugins/git/MergeWithGitSCMExtensionTest.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java index 7577d8b97b..719b5f39e6 100644 --- a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java +++ b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java @@ -64,7 +64,7 @@ public void testFailedMergeWithSCMExtension() throws Exception { // delete integration branch successfully and commit successfully repo.git.deleteBranch("integration"); repo.git.checkoutBranch("integration", "master"); - this.baseName=Constants.HEAD; + this.baseName = Constants.HEAD; this.baseHash = repo.git.revParse(baseName).name(); repo.commit(MASTER_FILE, "new content on integration branch", repo.johnDoe, repo.johnDoe, "Commit success!"); repo.git.checkout().ref("master").execute(); @@ -92,4 +92,4 @@ protected GitSCMExtension getExtension() { return new MergeWithGitSCMExtension(baseName,baseHash); } -} \ No newline at end of file +} From 2acc8394c60054a7316eb03623e3ae6db66df886 Mon Sep 17 00:00:00 2001 From: Loghi Date: Tue, 4 Feb 2020 12:31:17 +0530 Subject: [PATCH 040/101] Update src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java Co-Authored-By: Raihaan Shouhell --- .../java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java index 719b5f39e6..fb48328f4b 100644 --- a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java +++ b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java @@ -37,7 +37,7 @@ public void before() throws Exception { // make an initial commit to master and get hash this.baseHash=repo.commit(MASTER_FILE, repo.johnDoe, "Initial Commit"); // set the base name as HEAD - this.baseName=Constants.MASTER; + this.baseName = Constants.MASTER; project = setupBasicProject(repo); // create integration branch repo.git.branch("integration"); From efd676734b4ecdad3661526b4cd0880bab2caaff Mon Sep 17 00:00:00 2001 From: Loghi Date: Tue, 4 Feb 2020 12:31:34 +0530 Subject: [PATCH 041/101] Update src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java Co-Authored-By: Raihaan Shouhell --- .../java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java index fb48328f4b..4cefc6da83 100644 --- a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java +++ b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java @@ -35,7 +35,7 @@ public class MergeWithGitSCMExtensionTest extends GitSCMExtensionTest { public void before() throws Exception { repo = new TestGitRepo("repo", tmp.newFolder(), listener); // make an initial commit to master and get hash - this.baseHash=repo.commit(MASTER_FILE, repo.johnDoe, "Initial Commit"); + this.baseHash = repo.commit(MASTER_FILE, repo.johnDoe, "Initial Commit"); // set the base name as HEAD this.baseName = Constants.MASTER; project = setupBasicProject(repo); From f7414df7994b1375b7f9d92cf0924f5f146c148e Mon Sep 17 00:00:00 2001 From: Loghi Date: Tue, 4 Feb 2020 12:32:00 +0530 Subject: [PATCH 042/101] Update src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java Co-Authored-By: Mark Waite --- .../java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java index 4cefc6da83..c42d02c359 100644 --- a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java +++ b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java @@ -71,7 +71,7 @@ public void testFailedMergeWithSCMExtension() throws Exception { // as baseName and baseHash don't change in master branch, this commit should merge ! assertFalse("SCM polling should not detect any more changes after build", project.poll(listener).hasChanges()); - String conflictSha1= repo.commit(MASTER_FILE, "new content ", repo.johnDoe, repo.johnDoe, "Commit success!"); + String conflictSha1= repo.commit(MASTER_FILE, "new John Doe content will conflict", repo.johnDoe, repo.johnDoe, "Commit success!"); assertTrue("SCM polling should detect changes", project.poll(listener).hasChanges()); From 15e4907cb1ff71ef97ef41177c28f91ff4de3294 Mon Sep 17 00:00:00 2001 From: loghi Date: Tue, 4 Feb 2020 12:42:53 +0530 Subject: [PATCH 043/101] Removed unnecessary end new line. --- .../java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java index c42d02c359..d7817a5c04 100644 --- a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java +++ b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java @@ -92,4 +92,4 @@ protected GitSCMExtension getExtension() { return new MergeWithGitSCMExtension(baseName,baseHash); } -} +} \ No newline at end of file From 860b9919bba357f42be6cefbd8920db3a6fdb82e Mon Sep 17 00:00:00 2001 From: Loghi Date: Tue, 4 Feb 2020 22:53:09 +0530 Subject: [PATCH 044/101] Update src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java Co-Authored-By: Mark Waite --- .../java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java index d7817a5c04..55acc1e563 100644 --- a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java +++ b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java @@ -21,7 +21,6 @@ import java.util.List; import static org.junit.Assert.*; -import static org.junit.Assert.assertEquals; public class MergeWithGitSCMExtensionTest extends GitSCMExtensionTest { @@ -92,4 +91,4 @@ protected GitSCMExtension getExtension() { return new MergeWithGitSCMExtension(baseName,baseHash); } -} \ No newline at end of file +} From 210e3933377a4e80533e01273f3228a6b23a5fdc Mon Sep 17 00:00:00 2001 From: loghi Date: Tue, 4 Feb 2020 22:59:01 +0530 Subject: [PATCH 045/101] Optimized and removed wildcard imports. --- .../plugins/git/MergeWithGitSCMExtensionTest.java | 15 +++------------ 1 file changed, 3 insertions(+), 12 deletions(-) diff --git a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java index d7817a5c04..954d572f50 100644 --- a/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java +++ b/src/test/java/jenkins/plugins/git/MergeWithGitSCMExtensionTest.java @@ -3,25 +3,16 @@ import hudson.model.FreeStyleBuild; import hudson.model.FreeStyleProject; import hudson.model.Result; -import hudson.plugins.git.*; +import hudson.plugins.git.GitSCM; +import hudson.plugins.git.Revision; +import hudson.plugins.git.TestGitRepo; import hudson.plugins.git.extensions.GitSCMExtension; import hudson.plugins.git.extensions.GitSCMExtensionTest; -import hudson.plugins.git.extensions.impl.LocalBranch; -import hudson.plugins.git.extensions.impl.PreBuildMerge; import hudson.plugins.git.util.BuildData; -import junit.framework.TestCase; -import nl.jqno.equalsverifier.EqualsVerifier; import org.eclipse.jgit.lib.Constants; -import org.jenkinsci.plugins.gitclient.MergeCommand; import org.junit.Test; -import java.io.*; -import java.util.ArrayList; -import java.util.Collections; -import java.util.List; - import static org.junit.Assert.*; -import static org.junit.Assert.assertEquals; public class MergeWithGitSCMExtensionTest extends GitSCMExtensionTest { From 98df9a959e2fd9687014dc935d0d00c917edb1b9 Mon Sep 17 00:00:00 2001 From: Nicolas Terray Date: Thu, 6 Feb 2020 14:00:37 +0100 Subject: [PATCH 046/101] Restore Push notification documentation For unknown reason, the documentation chapter about "Push notification from repository" has disappeared. Currently we are forced to retrieve it via the wayback machine: https://web.archive.org/web/20190905084011/https://wiki.jenkins.io/display/JENKINS/Git+Plugin#GitPlugin-Pushnotificationfromrepository --- README.adoc | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/README.adoc b/README.adoc index 9f857b7bbb..7376a790e7 100644 --- a/README.adoc +++ b/README.adoc @@ -90,6 +90,29 @@ https://plugins.jenkins.io/credentials[Jenkins credentials plugin]. It does not support other credential types like secret text, secret file, or certificates. Select credentials from the job definition drop down menu or enter their identifiers in Pipeline job definitions. +[[GitPlugin-Pushnotificationfromrepository]] +=== Push notification from repository + +To minimize the delay between a push and a build, it is recommended to set up the post-receive hook in the repository to poke Jenkins when a new push occurs. To do this, add the following line in your hooks/post-receive file, where is the fully qualified URL you use when cloning this repository. + +.... +curl http://yourserver/git/notifyCommit?url=[&branches=branch1[,branch2]*][&sha1=] +.... + +This will scan all the jobs that: + +* Have Build Triggers > Poll SCM enabled. No polling Schedule is required. +* Are configured to build the repository at the specified URL +* Are configured to build the optionally specified branches or commit ID + +For jobs that meet these conditions, polling will be immediately triggered. If polling finds a change worthy of a build, a build will in turn be triggered. + +This allows a script to remain the same when jobs come and go in Jenkins. Or if you have multiple repositories under a single repository host application (such as Gitosis), you can share a single post-receive hook script with all the repositories. Finally, this URL doesn't require authentication even for secured Jenkins, because the server doesn't directly use anything that the client is sending. It runs polling to verify that there is a change, before it actually starts a build. + +When successful, the list of projects that were triggered is returned. + +`` is optional. If set, it will trigger a build immediately, without polling for changes. The advantage of this is that you then can have all pushes tested by jenkins, even when developers push at the same time. + [[enabling-jgit]] === Enabling JGit From 56a0206d4e650effceb070c09afa1b069c0e405d Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 6 Feb 2020 06:55:08 -0700 Subject: [PATCH 047/101] Refine the web hook and notify commit docs --- README.adoc | 28 +++++++++++++++++++--------- 1 file changed, 19 insertions(+), 9 deletions(-) diff --git a/README.adoc b/README.adoc index 7376a790e7..dfe0700388 100644 --- a/README.adoc +++ b/README.adoc @@ -90,28 +90,38 @@ https://plugins.jenkins.io/credentials[Jenkins credentials plugin]. It does not support other credential types like secret text, secret file, or certificates. Select credentials from the job definition drop down menu or enter their identifiers in Pipeline job definitions. +[[push-notification-from-repository]] [[GitPlugin-Pushnotificationfromrepository]] === Push notification from repository -To minimize the delay between a push and a build, it is recommended to set up the post-receive hook in the repository to poke Jenkins when a new push occurs. To do this, add the following line in your hooks/post-receive file, where is the fully qualified URL you use when cloning this repository. +To minimize the delay between a push and a build, configure the remote repository to use a Webhook to notify Jenkins of changs to the repository. +Refer to webhook documentation for your repository: +* link:https://plugins.jenkins.io/github#GitHubPlugin-GitHubhooktriggerforGITScmpolling[GitHub] +* link:https://plugins.jenkins.io/bitbucket[Bitbucket] +* link:https://plugins.jenkins.io/gitlab-branch-source[GitLab] +* link:https://github.com/jenkinsci/gitea-plugin/blob/master/docs/README.md[Gitea] + +Other git repositories can notify Jenkins with a post-receive hook in the repository to poke Jenkins when a new push occurs. +Add the following line in your hooks/post-receive file on the git server, replacing with the fully qualified URL you use when cloning the repository. .... -curl http://yourserver/git/notifyCommit?url=[&branches=branch1[,branch2]*][&sha1=] +curl http://yourserver/git/notifyCommit?url= .... This will scan all the jobs that: -* Have Build Triggers > Poll SCM enabled. No polling Schedule is required. +* Have Build Triggers > Poll SCM enabled. No polling schedule is required. * Are configured to build the repository at the specified URL -* Are configured to build the optionally specified branches or commit ID - -For jobs that meet these conditions, polling will be immediately triggered. If polling finds a change worthy of a build, a build will in turn be triggered. -This allows a script to remain the same when jobs come and go in Jenkins. Or if you have multiple repositories under a single repository host application (such as Gitosis), you can share a single post-receive hook script with all the repositories. Finally, this URL doesn't require authentication even for secured Jenkins, because the server doesn't directly use anything that the client is sending. It runs polling to verify that there is a change, before it actually starts a build. +For jobs that meet these conditions, polling will be triggered. +If polling finds a change worthy of a build, a build will be triggered. -When successful, the list of projects that were triggered is returned. +This allows a script to remain the same when jobs come and go in Jenkins. +Or if you have multiple repositories under a single repository host application (such as Gitosis, gitweb, or ), you can share a single post-receive hook script with all the repositories. +Finally, this URL doesn't require authentication even for secured Jenkins, because the server doesn't directly use anything that the client is sending. +It runs polling to verify that there is a change before it actually starts a build. -`` is optional. If set, it will trigger a build immediately, without polling for changes. The advantage of this is that you then can have all pushes tested by jenkins, even when developers push at the same time. +When notifyCommit is successful, the list of triggered projects is returned. [[enabling-jgit]] === Enabling JGit From 95321181e05cb01d5a49c840afbb9c39739b49d6 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 6 Feb 2020 07:01:37 -0700 Subject: [PATCH 048/101] Add required blank line before list --- README.adoc | 1 + 1 file changed, 1 insertion(+) diff --git a/README.adoc b/README.adoc index dfe0700388..532320d558 100644 --- a/README.adoc +++ b/README.adoc @@ -96,6 +96,7 @@ Select credentials from the job definition drop down menu or enter their identif To minimize the delay between a push and a build, configure the remote repository to use a Webhook to notify Jenkins of changs to the repository. Refer to webhook documentation for your repository: + * link:https://plugins.jenkins.io/github#GitHubPlugin-GitHubhooktriggerforGITScmpolling[GitHub] * link:https://plugins.jenkins.io/bitbucket[Bitbucket] * link:https://plugins.jenkins.io/gitlab-branch-source[GitLab] From fc70671dd16663632835fa8984b100b590b4dd02 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 6 Feb 2020 07:09:04 -0700 Subject: [PATCH 049/101] Link to the git scm book --- README.adoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.adoc b/README.adoc index 532320d558..21010577a2 100644 --- a/README.adoc +++ b/README.adoc @@ -102,7 +102,7 @@ Refer to webhook documentation for your repository: * link:https://plugins.jenkins.io/gitlab-branch-source[GitLab] * link:https://github.com/jenkinsci/gitea-plugin/blob/master/docs/README.md[Gitea] -Other git repositories can notify Jenkins with a post-receive hook in the repository to poke Jenkins when a new push occurs. +Other git repositories can use a link:https://git-scm.com/book/en/v2/Customizing-Git-Git-Hooks[post-receive hook] in the remote repository to notify Jenkins of changes. Add the following line in your hooks/post-receive file on the git server, replacing with the fully qualified URL you use when cloning the repository. .... From 4e5bb7aadf369864e82c1f6fc10838cfb42f9e03 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 6 Feb 2020 07:09:35 -0700 Subject: [PATCH 050/101] Show file name in fixed font --- README.adoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.adoc b/README.adoc index 21010577a2..0e55f705c1 100644 --- a/README.adoc +++ b/README.adoc @@ -103,7 +103,7 @@ Refer to webhook documentation for your repository: * link:https://github.com/jenkinsci/gitea-plugin/blob/master/docs/README.md[Gitea] Other git repositories can use a link:https://git-scm.com/book/en/v2/Customizing-Git-Git-Hooks[post-receive hook] in the remote repository to notify Jenkins of changes. -Add the following line in your hooks/post-receive file on the git server, replacing with the fully qualified URL you use when cloning the repository. +Add the following line in your `hooks/post-receive` file on the git server, replacing with the fully qualified URL you use when cloning the repository. .... curl http://yourserver/git/notifyCommit?url= From df92978b3d7677a18a19132485e0a2872806026a Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 6 Feb 2020 07:09:53 -0700 Subject: [PATCH 051/101] show file name in fixed font --- README.adoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.adoc b/README.adoc index 0e55f705c1..dd6b9158b7 100644 --- a/README.adoc +++ b/README.adoc @@ -118,7 +118,7 @@ For jobs that meet these conditions, polling will be triggered. If polling finds a change worthy of a build, a build will be triggered. This allows a script to remain the same when jobs come and go in Jenkins. -Or if you have multiple repositories under a single repository host application (such as Gitosis, gitweb, or ), you can share a single post-receive hook script with all the repositories. +Or if you have multiple repositories under a single repository host application (such as Gitosis), you can share a single post-receive hook script with all the repositories. Finally, this URL doesn't require authentication even for secured Jenkins, because the server doesn't directly use anything that the client is sending. It runs polling to verify that there is a change before it actually starts a build. From 767d663041dbd897d2e15d0bd3675487f7ea4331 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 6 Feb 2020 14:16:10 -0700 Subject: [PATCH 052/101] Add link ID from wiki page --- README.adoc | 1 + 1 file changed, 1 insertion(+) diff --git a/README.adoc b/README.adoc index dd6b9158b7..cb0d768f0e 100644 --- a/README.adoc +++ b/README.adoc @@ -31,6 +31,7 @@ toc::[] Release notes are recorded in https://github.com/jenkinsci/git-plugin/releases[GitHub Releases] since July 1, 2019 (git plugin 3.10.1 and later). Prior release notes are recorded in the git plugin repository link:CHANGELOG.adoc#changelog-moved-to-github-releases[change log]. +[[GitPlugin-ProjectConfiguration]] [[configuration]] == Configuration From 47541b0b45b6b025683c6ed3fa4c6ba94afc9b7a Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 6 Feb 2020 14:16:42 -0700 Subject: [PATCH 053/101] Better phrasing of notifyCommit script portability --- README.adoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.adoc b/README.adoc index cb0d768f0e..f8a9e6f02a 100644 --- a/README.adoc +++ b/README.adoc @@ -118,7 +118,7 @@ This will scan all the jobs that: For jobs that meet these conditions, polling will be triggered. If polling finds a change worthy of a build, a build will be triggered. -This allows a script to remain the same when jobs come and go in Jenkins. +This allows a notify script to remain the same for all Jenkins jobs. Or if you have multiple repositories under a single repository host application (such as Gitosis), you can share a single post-receive hook script with all the repositories. Finally, this URL doesn't require authentication even for secured Jenkins, because the server doesn't directly use anything that the client is sending. It runs polling to verify that there is a change before it actually starts a build. From 8ce36c8b3a98661fc4641bfe4ccdea26b778ba4b Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 6 Feb 2020 14:17:07 -0700 Subject: [PATCH 054/101] Document global configuration settings --- README.adoc | 34 ++++++++++++++++++++++++++++++++++ 1 file changed, 34 insertions(+) diff --git a/README.adoc b/README.adoc index f8a9e6f02a..b2f635c589 100644 --- a/README.adoc +++ b/README.adoc @@ -131,6 +131,40 @@ When notifyCommit is successful, the list of triggered projects is returned. See the https://plugins.jenkins.io/git-client[git client plugin documentation] for instructions to enable JGit. JGit becomes available throughout Jenkins once it has been enabled. +[[GitPlugin-Configuration]] +[[global-configuration]] +=== Global Configuration + +In the `Configure System` page, the Git Plugin provides the following options: + +[[global-config-user-name]] +Global Config user.name Value:: + + Defines the default git user name that will be assigned when git commits a change from Jenkins. + For example, `Janice Examplesperson`. + This can be overridden by individual projects with the <> extension. + +[[global-config-user-email]] +Global Config user.email Value:: + + Defines the default git user e-mail that will be assigned when git commits a change from Jenkins. + For example, `janice.examplesperson@example.com`. + This can be overridden by individual projects with the <> extension. + +[[create-new-accounts-based-on-author-email]] +Create new accounts based on author/committer's email:: + + New user accounts are created in Jenkins for committers and authors identified in changelogs. + The new user accounts are added to the internal Jenkins database. + The e-mail address is used as the id of the account. + +[[show-the-entire-commit-summary-in-changes]] +Show the entire commit summary in changes:: + + The `changes` page for each job would truncate the change summary prior to git plugin 3.0. + With the release of git plugin 3.0, the default was changed to show the complete change summary. + Administrators that want to restore the old behavior may disable this setting. + [[repository-browser]] === Repository Browser From a433789c5b5f84a0061d88d6b70abcefdcc44ef1 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 6 Feb 2020 14:17:53 -0700 Subject: [PATCH 055/101] Describe workspace polling and fast remote polling --- README.adoc | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/README.adoc b/README.adoc index b2f635c589..d8a49fdb48 100644 --- a/README.adoc +++ b/README.adoc @@ -706,6 +706,10 @@ When this extension is enabled, the polling is performed from a cloned copy of t If this option is selected, polling will use a workspace instead of using `ls-remote`. +By default, the plugin polls by executing a polling process or thread on the Jenkins master. +If the Jenkins master does not have a git installation, the administrator may <> to use a pure Java git implementation for polling. +In addition, the administrator may need to <> to prevent use of command line git on the Jenkins master. + [[merge-extensions]] === Merge Extensions From f9c885112a7374161611c7e77293bb6276768335 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 6 Feb 2020 14:18:25 -0700 Subject: [PATCH 056/101] Command line git is the reference implementation --- README.adoc | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/README.adoc b/README.adoc index d8a49fdb48..684211b932 100644 --- a/README.adoc +++ b/README.adoc @@ -903,6 +903,12 @@ Some git plugin settings can only be controlled from command line properties set The default git timeout value (in minutes) can be overridden by the `org.jenkinsci.plugins.gitclient.Git.timeOut` property (see https://issues.jenkins-ci.org/browse/JENKINS-11286[JENKINS-11286])). The property should be set on the master and on all agents to have effect (see https://issues.jenkins-ci.org/browse/JENKINS-22547[JENKINS-22547]). +[[GitPlugin-WhyNotJGit]] +Command line git is the reference git implementation in the git plugin and the git client plugin. +Command line git provides the most functionality and is the most stable implementation. +Some installations may not want to install command line git and may want to disable the command line git implementation. +Administrators may disable command line git with the property `org.jenkinsci.plugins.gitclient.Git.useCLI=false`. + [[git-publisher]] == Git Publisher From 230886e8bec511a0da5a2f5eae74594c9ef99af8 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Mon, 10 Feb 2020 05:36:26 -0700 Subject: [PATCH 057/101] Remove incorrectly placed word from docs --- README.adoc | 1 - 1 file changed, 1 deletion(-) diff --git a/README.adoc b/README.adoc index 684211b932..58085e7703 100644 --- a/README.adoc +++ b/README.adoc @@ -419,7 +419,6 @@ Stash is now called *BitBucket Server*. Repository browser for git repositories hosted by link:https://www.atlassian.com/software/bitbucket[BitBucket Server]. Options include: -stash [[stash-url]] URL:: From db9e8eef65d24f3eb2739c3f2d79a1f754dbee70 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Mon, 10 Feb 2020 05:38:39 -0700 Subject: [PATCH 058/101] Fix secondary anchor points to correct syntax See https://asciidoctor.org/docs/user-manual/#multiple-anchors for details --- README.adoc | 19 ++++++++----------- 1 file changed, 8 insertions(+), 11 deletions(-) diff --git a/README.adoc b/README.adoc index 58085e7703..35135d5749 100644 --- a/README.adoc +++ b/README.adoc @@ -31,9 +31,8 @@ toc::[] Release notes are recorded in https://github.com/jenkinsci/git-plugin/releases[GitHub Releases] since July 1, 2019 (git plugin 3.10.1 and later). Prior release notes are recorded in the git plugin repository link:CHANGELOG.adoc#changelog-moved-to-github-releases[change log]. -[[GitPlugin-ProjectConfiguration]] -[[configuration]] -== Configuration +[#configuration] +== [[GitPlugin-ProjectConfiguration]]Configuration [[using-repositories]] === Repositories @@ -91,9 +90,8 @@ https://plugins.jenkins.io/credentials[Jenkins credentials plugin]. It does not support other credential types like secret text, secret file, or certificates. Select credentials from the job definition drop down menu or enter their identifiers in Pipeline job definitions. -[[push-notification-from-repository]] -[[GitPlugin-Pushnotificationfromrepository]] -=== Push notification from repository +[#push-notification-from-repository] +=== [[GitPlugin-Pushnotificationfromrepository]]Push notification from repository To minimize the delay between a push and a build, configure the remote repository to use a Webhook to notify Jenkins of changs to the repository. Refer to webhook documentation for your repository: @@ -125,15 +123,14 @@ It runs polling to verify that there is a change before it actually starts a bui When notifyCommit is successful, the list of triggered projects is returned. -[[enabling-jgit]] +[#enabling-jgit] === Enabling JGit -See the https://plugins.jenkins.io/git-client[git client plugin documentation] for instructions to enable JGit. +See the link:https://plugins.jenkins.io/git-client/#enabling-jgit[git client plugin documentation] for instructions to enable JGit. JGit becomes available throughout Jenkins once it has been enabled. -[[GitPlugin-Configuration]] -[[global-configuration]] -=== Global Configuration +[#global-configuration] +=== [[GitPlugin-Configuration]]Global Configuration In the `Configure System` page, the Git Plugin provides the following options: From 10bc60c2343854474427f1219cfe2bb8b31cee3e Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Mon, 10 Feb 2020 05:41:47 -0700 Subject: [PATCH 059/101] Use preferred syntax for each primary header id The [[id-text]] is allowed, but [#id-text] is listed in examples more frequently. Also add id values to some headings which did not have them before. --- README.adoc | 133 +++++++++++++++++++++++++++------------------------- 1 file changed, 70 insertions(+), 63 deletions(-) diff --git a/README.adoc b/README.adoc index 35135d5749..8997952c94 100644 --- a/README.adoc +++ b/README.adoc @@ -9,7 +9,7 @@ link:https://plugins.jenkins.io/git[image:https://img.shields.io/jenkins/plugin/ link:https://github.com/jenkinsci/git-plugin/releases/latest[image:https://img.shields.io/github/release/jenkinsci/git-plugin.svg?label=changelog[GitHub release]] link:https://gitter.im/jenkinsci/git-plugin[image:https://badges.gitter.im/jenkinsci/git-plugin.svg[Gitter]] -[[introduction]] +[#introduction] == Introduction [.float-group] @@ -25,7 +25,7 @@ It can poll, fetch, checkout, branch, list, merge, tag, and push repositories. toc::[] -[[changelog]] +[#changelog] == Changelog in https://github.com/jenkinsci/git-plugin/releases[GitHub Releases] Release notes are recorded in https://github.com/jenkinsci/git-plugin/releases[GitHub Releases] since July 1, 2019 (git plugin 3.10.1 and later). @@ -34,7 +34,7 @@ Prior release notes are recorded in the git plugin repository link:CHANGELOG.ado [#configuration] == [[GitPlugin-ProjectConfiguration]]Configuration -[[using-repositories]] +[#using-repositories] === Repositories The git plugin fetches commits from one or more remote repositories and performs a checkout in the agent workspace. @@ -82,7 +82,7 @@ The refspec value `+refs/heads/master:refs/remotes/origin/master +refs/heads/dev + Refer to the link:https://git-scm.com/book/en/v2/Git-Internals-The-Refspec[git refspec documentation] for more refspec details. -[[using-credentials]] +[#using-credentials] === Using Credentials The git plugin supports username / password credentials and private key credentials provided by the @@ -162,7 +162,7 @@ Show the entire commit summary in changes:: With the release of git plugin 3.0, the default was changed to show the complete change summary. Administrators that want to restore the old behavior may disable this setting. -[[repository-browser]] +[#repository-browser] === Repository Browser A Repository Browser adds links in "changes" views within Jenkins to an external system for browsing the details of those changes. @@ -170,7 +170,7 @@ The "Auto" selection attempts to infer the repository browser from the "Reposito Repository browsers include: -[[assemblaweb-repository-browser]] +[#assemblaweb-repository-browser] ==== AssemblaWeb Repository browser for git repositories hosted by link:https://www.assembla.com/home[Assembla]. @@ -182,7 +182,7 @@ Assembla Git URL:: Root URL serving this Assembla repository. For example, `\https://app.assembla.com/spaces/git-plugin/git/source` -[[fisheye-repository-browser]] +[#fisheye-repository-browser] ==== FishEye Repository browser for git repositories hosted by link:https://www.atlassian.com/software/fisheye[Atlassian Fisheye]. @@ -194,14 +194,14 @@ URL:: Root URL serving this FishEye repository. For example, `\https://fisheye.example.com/browser/my-project` -[[gitlab-com-repository-browser]] +[#gitlab-com-repository-browser] ==== GitLab Repository browser for git repositories hosted on link:https://gitlab.com[GitLab.com]. No options can be configured for this repository browser. Users hosting their own instances of GitLab should use the <> browser instead. -[[gitea-repository-browser]] +[#gitea-repository-browser] ==== Gitea Repository browser for git repositories hosted by link:https://gitea.io/[Gitea]. @@ -213,7 +213,7 @@ Repository URL:: Root URL serving this gitea repository. For example, `\https://gitea.example.com/username/project-name` -[[kiln-repository-browser]] +[#kiln-repository-browser] ==== Kiln Repository browser for git repositories hosted by link:http://www.fogbugz.com/version-control[Kiln]. @@ -225,7 +225,7 @@ URL:: Root URL serving this Kiln repository. For example, `\https://kiln.example.com/username/my-project` -[[visual-studio-team-services-repository-browser]] +[#visual-studio-team-services-repository-browser] ==== Microsoft Team Foundation Server/Visual Studio Team Services Repository browser for git repositories hosted by link:https://azure.microsoft.com/en-us/solutions/devops/[Azure DevOps]. @@ -237,7 +237,7 @@ URL or name:: Root URL serving this Azure DevOps repository. For example, `\https://example.visualstudio.com/_git/my-project.` -[[bitbucketweb-repository-browser]] +[bitbucketweb-repository-browser] ==== bitbucketweb Repository browser for git repositories hosted by link:https://bitbucket.org/[Bitbucket]. @@ -249,7 +249,7 @@ URL:: Root URL serving this Bitbucket repository. For example, `\https://bitbucket.example.com/username/my-project` -[[cgit-repository-browser]] +[#cgit-repository-browser] ==== cgit Repository browser for git repositories hosted by link:https://git.zx2c4.com/cgit/[cgit]. @@ -261,7 +261,7 @@ URL:: Root URL serving this cgit repository. For example, `\https://git.zx2c4.com/cgit/` -[[gitblit-repository-browser]] +[#gitblit-repository-browser] ==== gitblit [[gitblit-url]] @@ -276,7 +276,7 @@ Project name in GitBlit:: Name of the GitBlit project. For example, `my-project` -[[githubweb-repository-browser]] +[#githubweb-repository-browser] ==== githubweb Repository browser for git repositories hosted by link:https://github.com//[GitHub]. @@ -288,7 +288,7 @@ GitHub root url:: Root URL serving this GitHub repository. For example, `\https://github.example.com/username/my-project` -[[gitiles-repository-browser]] +[#gitiles-repository-browser] ==== gitiles Repository browser for git repositories hosted by link:https://gerrit.googlesource.com/gitiles/[Gitiles]. @@ -300,7 +300,7 @@ gitiles root url:: Root URL serving this Gitiles repository. For example, `\https://gerrit.googlesource.com/gitiles/` -[[gitlab-self-hosted-repository-browser]] +[#gitlab-self-hosted-repository-browser] ==== gitlab Repository browser for git repositories hosted by link:https://gitlab.com/[GitLab]. @@ -319,7 +319,7 @@ Version:: If you don't specify a version, a modern version of GitLab (>= 8.0) is assumed. For example, `12.6` -[[gitlist-repository-browser]] +[#gitlist-repository-browser] ==== gitlist Repository browser for git repositories hosted by link:https://gitlist.org/[GitList]. @@ -331,7 +331,7 @@ URL:: Root URL serving this GitList repository. For example, `\https://gitlist.example.com/username/my-project` -[[gitoriousweb-repository-browser]] +[#gitoriousweb-repository-browser] ==== gitoriousweb Gitorious was acquired in 2015. @@ -343,7 +343,7 @@ URL:: Root URL serving this Gitorious repository. For example, `\https://gitorious.org/username/my-project` -[[gitweb-repository-browser]] +[#gitweb-repository-browser] ==== gitweb Repository browser for git repositories hosted by link:https://git-scm.com/docs/gitweb[GitWeb]. @@ -355,7 +355,7 @@ URL:: Root URL serving this GitWeb repository. For example, `\https://gitweb.example.com/username/my-project` -[[gogs-repository-browser]] +[#gogs-repository-browser] ==== gogs Repository browser for git repositories hosted by link:https://gogs.io/[Gogs]. @@ -367,7 +367,7 @@ URL:: Root URL serving this Gogs repository. For example, `\https://gogs.example.com/username/my-project` -[[phabricator-repository-browser]] +[#phabricator-repository-browser] ==== phabricator Repository browser for git repositories hosted by link:https://www.phacility.com/phabricator/[Phacility Phabricator]. @@ -385,7 +385,7 @@ Repository name in Phab:: Name of the Phabricator repository. For example, `my-project` -[[redmineweb-repository-browser]] +[#redmineweb-repository-browser] ==== redmineweb Repository browser for git repositories hosted by link:https://www.redmine.org/[Redmine]. @@ -397,7 +397,7 @@ URL:: Root URL serving this Redmine repository. For example, `\https://redmine.example.com/username/projects/my-project/repository` -[[rhodecode-repository-browser]] +[#rhodecode-repository-browser] ==== rhodecode Repository browser for git repositories hosted by link:https://thodecode.com/[RhodeCode]. @@ -409,7 +409,7 @@ URL:: Root URL serving this RhodeCode repository. For example, `\https://rhodecode.example.com/username/my-project` -[[stash-repository-browser]] +[#stash-repository-browser] ==== stash Stash is now called *BitBucket Server*. @@ -422,7 +422,7 @@ URL:: Root URL serving this Stash repository. For example, `\https://stash.example.com/username/my-project` -[[viewgit-repository-browser]] +[#viewgit-repository-browser] ==== viewgit Repository browser for git repositories hosted by link:https://www.openhub.net/p/viewgit[viewgit]. @@ -440,7 +440,7 @@ Project Name in ViewGit:: ViewGit project name. For example, `my-project` -[[extensions]] +[#extensions] == Extensions Extensions add new behavior or modify existing plugin behavior for different uses. @@ -456,10 +456,10 @@ Extensions include: - <> - <> -[[clone-extensions]] +[#clone-extensions] === Clone Extensions -[[advanced-clone-behaviours]] +[#advanced-clone-behaviours] ==== Advanced clone behaviours Advanced clone behaviors modify the `link:https://git-scm.com/docs/git-clone[git clone]` and `link:https://git-scm.com/docs/git-fetch[git fetch]` commands. @@ -504,10 +504,10 @@ Fetch tags:: Deselect this to perform a clone without tags, saving time and disk space when you want to access only what is specified by the refspec, without considering any repository tags. -[[checkout-extensions]] +[#checkout-extensions] === Checkout Extensions -[[advanced-checkout-behaviors]] +[#advanced-checkout-behaviors] ==== Advanced checkout behaviors Advanced checkout behaviors modify the `link:https://git-scm.com/docs/git-checkout[git checkout]` command. @@ -519,7 +519,7 @@ Timeout (in minutes) for checkout operation:: The checkout is stopped if the timeout is exceeded. Checkout timeout is usually only required with slow file systems or large repositories. -[[advanced-sub-modules-behaviours]] +[#advanced-sub-modules-behaviours] ==== Advanced sub-modules behaviours Advanced sub-modules behaviors modify the `link:https://git-scm.com/docs/git-submodule[git submodule]` commands. @@ -582,7 +582,7 @@ Number of threads to use when updating submodules:: Number of parallel processes to be used when updating submodules. Default is to use a single thread for submodule updates -[[checkout-to-a-sub-directory]] +[#checkout-to-a-sub-directory] ==== Checkout to a sub-directory Checkout to a subdirectory of the workspace instead of using the workspace root. @@ -596,7 +596,7 @@ Local subdirectory for repo:: Name of the local directory (relative to the workspace root) for the git repository checkout. If left empty, the workspace root itself will be used. -[[checkout-to-specific-local-branch]] +[#checkout-to-specific-local-branch] ==== Checkout to specific local branch Branch name:: @@ -605,13 +605,13 @@ Branch name:: If value is an empty string or "**", then the branch name is computed from the remote branch without the origin. In that case, a remote branch 'origin/master' will be checked out to a local branch named 'master', and a remote branch 'origin/develop/new-feature' will be checked out to a local branch named 'develop/new-feature'. -[[wipe-out-repository-and-force-clone]] +[#wipe-out-repository-and-force-clone] ==== Wipe out repository and force clone Delete the contents of the workspace before build and before checkout. Deletes the git repository inside the workspace and will force a full clone. -[[clean-after-checkout]] +[clean-after-checkout] ==== Clean after checkout Clean the workspace *after* every checkout by deleting all untracked files and directories, including those which are specified in `.gitignore`. @@ -627,7 +627,7 @@ Delete untracked nested repositories:: This is implemented in command line git as `git clean -xffd`. Refer to the link:https://git-scm.com/docs/git-clean[git clean manual page] for more information. -[[clean-before-checkout]] +[#clean-before-checkout] ==== Clean before checkout Clean the workspace *before* every checkout by deleting all untracked files and directories, including those which are specified in .gitignore. @@ -643,19 +643,19 @@ Delete untracked nested repositories:: This is implemented in command line git as `git clean -xffd`. Refer to the link:https://git-scm.com/docs/git-clean[git clean manual page] for more information. -[[git-lfs-pull-after-checkout]] +[#git-lfs-pull-after-checkout] ==== Git LFS pull after checkout Enable https://git-lfs.github.com/[git large file support] for the workspace by pulling large files after the checkout completes. Requires that the master and each agent performing an LFS checkout have installed `git lfs`. -[[changelog-extensions]] +[#changelog-extensions] === Changelog Extensions The plugin can calculate the source code differences between two builds. Changelog extensions adapt the changelog calculations for different cases. -[[calculate-changelog-against-a-specific-branch]] +[#calculate-changelog-against-a-specific-branch] ==== Calculate changelog against a specific branch 'Calculate changelog against a specific branch' uses the specified branch to compute the changelog instead of computing it based on the previous build. @@ -669,32 +669,32 @@ Name of branch:: Name of the branch used for the changelog calculation within the named repository. -[[use-commit-author-in-changelog]] +[#use-commit-author-in-changelog] ==== Use commit author in changelog The default behavior is to use the Git commit's "Committer" value in build changesets. If this option is selected, the git commit's "Author" value is used instead. -[[tagging-extensions]] +[#tagging-extensions] === Tagging Extensions -[[create-a-tag-for-every-build]] +[#create-a-tag-for-every-build] ==== Create a tag for every build Create a tag in the workspace for every build to unambiguously mark the commit that was built. You can combine this with Git publisher to push the tags to the remote repository. -[[build-initiation-extensions]] +[#build-initiation-extensions] === Build initiation extensions The git plugin can start builds based on many different conditions. -[[dont-trigger-a-build-on-commit-notifications]] +[#dont-trigger-a-build-on-commit-notifications] ==== Don't trigger a build on commit notifications If checked, this repository will be ignored when the notifyCommit URL is accessed whether the repository matches or not. -[[force-polling-using-workspace]] +[#force-polling-using-workspace] ==== Force polling using workspace The git plugin polls remotely using `ls-remote` when configured with a single branch (no wildcards!). @@ -706,10 +706,10 @@ By default, the plugin polls by executing a polling process or thread on the Jen If the Jenkins master does not have a git installation, the administrator may <> to use a pure Java git implementation for polling. In addition, the administrator may need to <> to prevent use of command line git on the Jenkins master. -[[merge-extensions]] +[#merge-extensions] === Merge Extensions -[[merge-before-build]] +[#merge-before-build] ==== Merge before build These options allow you to perform a merge to a particular branch before building. @@ -746,7 +746,7 @@ Fast-forward mode:: * `-ff-only`: fast-forward without any fallback * `--no-ff`: merge commit always, even if a fast-forward would have been allowed -[[custom-user-name-e-mail-address]] +[#custom-user-name-e-mail-address] ==== Custom user name/e-mail address user.name:: @@ -761,7 +761,7 @@ user.email:: in the workspace. If given, git config user.email [this] is called before builds. This overrides whatever is in the global settings. -[[polling-ignores-commits-from-certain-users]] +[#polling-ignores-commits-from-certain-users] ==== Polling ignores commits from certain users These options allow you to perform a merge to a particular branch before building. @@ -778,7 +778,7 @@ Excluded Users:: Each exclusion uses literal pattern matching, and must be separated by a new line. -[[polling-ignores-commits-in-certain-paths]] +[#polling-ignores-commits-in-certain-paths] ==== Polling ignores commits in certain paths If set and Jenkins is configured to poll for changes, Jenkins will pay attention to included and/or excluded files and/or folders when determining if a build needs to be triggered. @@ -797,7 +797,7 @@ Excluded Regions:: Each exclusion uses java regular expression pattern matching, and must be separated by a new line. An empty list excludes nothing. -[[polling-ignores-commits-with-certain-messages]] +[#polling-ignores-commits-with-certain-messages] ==== Polling ignores commits with certain messages Excluded Messages:: @@ -806,12 +806,12 @@ Excluded Messages:: This can be used to exclude commits done by the build itself from triggering another build, assuming the build server commits the change with a distinct message. You can create more complex patterns using embedded flag expressions. -[[prune-stale-remote-tracking-branches]] +[#prune-stale-remote-tracking-branches] ==== Prune stale remote tracking branches Runs `link:https://git-scm.com/docs/git-remote[git remote prune]` for each remote to prune obsolete local branches. -[[sparse-checkout-paths]] +[#sparse-checkout-paths] ==== Sparse Checkout paths Specify the paths that you'd like to sparse checkout. @@ -824,7 +824,7 @@ Path:: File or directory to be included in the checkout -[[strategy-for-choosing-what-to-build]] +[#strategy-for-choosing-what-to-build] ==== Strategy for choosing what to build When you are interested in using a job to build multiple branches, you can choose how Jenkins chooses the branches to build and the order they should be built. @@ -853,33 +853,36 @@ Inverse:: This is useful, for example, when you have jobs building your master and various release branches and you want a second job which builds all new feature branches. For example, branches which do not match these patterns without redundantly building master and the release branches again each time they change. -[[deprecated-extensions]] +[#deprecated-extensions] === Deprecated Extensions -[[custom-scm-name---deprecated]] +[#custom-scm-name---deprecated] ==== Custom SCM name - *Deprecated* Unique name for this SCM. Was needed when using Git within the Multi SCM plugin. Pipeline is the robust and feature-rich way to checkout from multiple repositories in a single job. -[[environment-variables]] +[#environment-variables] == Environment Variables The git plugin assigns values to environment variables in several contexts. Environment variables are assigned in Freestyle, Pipeline, Multibranch Pipeline, and Organization Folder projects. +[#branch-variables] === Branch Variables GIT_BRANCH:: Name of branch being built including remote name, as in `origin/master` GIT_LOCAL_BRANCH:: Name of branch being built without remote name, as in `master` +[#commit-variables] === Commit Variables GIT_COMMIT:: SHA-1 of the commit used in this build GIT_PREVIOUS_COMMIT:: SHA-1 of the commit used in the preceding build of this project GIT_PREVIOUS_SUCCESSFUL_COMMIT:: SHA-1 of the commit used in the most recent successful build of this project +[#system-configuration-variables] === System Configuration Variables GIT_URL:: Remote URL of the first git repository in this workspace @@ -889,11 +892,12 @@ GIT_AUTHOR_NAME:: Author name that will be used for **new commits in this worksp GIT_COMMITTER_EMAIL:: Committer e-mail address that will be used for **new commits in this workspace*** GIT_COMMITTER_NAME:: Committer name that will be used for **new commits in this workspace** -[[properties]] +[#properties] == Properties Some git plugin settings can only be controlled from command line properties set at Jenkins startup. +[#default-timeout] === Default timeout The default git timeout value (in minutes) can be overridden by the `org.jenkinsci.plugins.gitclient.Git.timeOut` property (see https://issues.jenkins-ci.org/browse/JENKINS-11286[JENKINS-11286])). @@ -905,7 +909,7 @@ Command line git provides the most functionality and is the most stable implemen Some installations may not want to install command line git and may want to disable the command line git implementation. Administrators may disable command line git with the property `org.jenkinsci.plugins.gitclient.Git.useCLI=false`. -[[git-publisher]] +[#git-publisher] == Git Publisher The Jenkins git plugin provides a "git publisher" as a post-build action. @@ -914,6 +918,7 @@ The git publisher can push commits or tags from the workspace of a Freestyle pro The git publisher is **only available** for Freestyle projects. It is **not available** for Pipeline, Multibranch Pipeline, Organization Folder, or any other job type other than Freestyle. +[#git-publisher-options] === Git Publisher Options The git publisher behaviors are controlled by options that can be configured as part of the Jenkins job. @@ -938,6 +943,7 @@ Force Push:: If the commits from the local workspace should overwrite commits on the remote repository, enable this option. It will request that the remote repository destroy history and replace it with history from the workspace. +[#git-publisher-tags-options] ==== Git Publisher Tags Options The git publisher can push tags from the workspace to the remote repository. @@ -974,6 +980,7 @@ Tag remote name:: This option defines which remote should receive the push. This is typically `origin`, though it could be any one of the remote names defined when the plugin performs the checkout. +[#git-publisher-branches-options] ==== Git Publisher Branches Options The git publisher can push branches from the workspace to the remote repository. @@ -1002,7 +1009,7 @@ The commits in the local workspace have been evaluated by the job. The most recent commits from the remote repository have not been evaluated by the job. Users may find that the risk of pushing an untested configuration is less than the risk of delaying the visibility of the changes which have been evaluated by the job. -[[combining-repositories]] +[#combining-repositories] == Combining repositories A single reference repository may contain commits from multiple repositories. @@ -1022,13 +1029,13 @@ Those commands create a single bare repository with the current commits from all If that reference repository is used in the advanced clone options link:#clone-reference-repository-path[clone reference repository], it will reduce data transfer and disc use for the parent repository. If that reference repository is used in the submodule options link:#submodule-reference-repository-path[clone reference repository], it will reduce data transfer and disc use for the submodule repositories. -[[bug-reports]] +[#bug-reports] == Bug Reports Report issues and enhancements in the https://issues.jenkins-ci.org[Jenkins issue tracker]. -[[contributing-to-the-plugin]] +[#contributing-to-the-plugin] == Contributing to the Plugin Refer to link:CONTRIBUTING.adoc#contributing-to-the-git-plugin[contributing to the plugin] for contribution guidelines. From 0fc6f4de360d263b79d4e20e9670b4ee2d53326e Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Mon, 10 Feb 2020 05:54:11 -0700 Subject: [PATCH 060/101] Better phrasing in polling description --- README.adoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.adoc b/README.adoc index 8997952c94..d4e087fc6a 100644 --- a/README.adoc +++ b/README.adoc @@ -119,7 +119,7 @@ If polling finds a change worthy of a build, a build will be triggered. This allows a notify script to remain the same for all Jenkins jobs. Or if you have multiple repositories under a single repository host application (such as Gitosis), you can share a single post-receive hook script with all the repositories. Finally, this URL doesn't require authentication even for secured Jenkins, because the server doesn't directly use anything that the client is sending. -It runs polling to verify that there is a change before it actually starts a build. +It polls to verify that there is a change before it actually starts a build. When notifyCommit is successful, the list of triggered projects is returned. From 65f0e0ded8b23e28a5d4a88d82071af92c4a0dd9 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Mon, 10 Feb 2020 05:54:32 -0700 Subject: [PATCH 061/101] Explain results of prune, not command that is run --- README.adoc | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/README.adoc b/README.adoc index d4e087fc6a..fce8c53655 100644 --- a/README.adoc +++ b/README.adoc @@ -809,7 +809,8 @@ Excluded Messages:: [#prune-stale-remote-tracking-branches] ==== Prune stale remote tracking branches -Runs `link:https://git-scm.com/docs/git-remote[git remote prune]` for each remote to prune obsolete local branches. +Removes remote tracking branches from the local workspace if they no longer exist on the remote. +See `link:https://git-scm.com/docs/git-remote#Documentation/git-remote.txt-empruneem[git remote prune]` and `link:https://git-scm.com/docs/git-fetch#_pruning[git fetch --prune]` for more details. [#sparse-checkout-paths] ==== Sparse Checkout paths From 3614b78ecd278aaa54f265be334d8669b2852fa7 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Mon, 10 Feb 2020 05:57:44 -0700 Subject: [PATCH 062/101] Remove extra parenthesis in README --- README.adoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.adoc b/README.adoc index fce8c53655..ebfea6b51e 100644 --- a/README.adoc +++ b/README.adoc @@ -901,7 +901,7 @@ Some git plugin settings can only be controlled from command line properties set [#default-timeout] === Default timeout -The default git timeout value (in minutes) can be overridden by the `org.jenkinsci.plugins.gitclient.Git.timeOut` property (see https://issues.jenkins-ci.org/browse/JENKINS-11286[JENKINS-11286])). +The default git timeout value (in minutes) can be overridden by the `org.jenkinsci.plugins.gitclient.Git.timeOut` property (see https://issues.jenkins-ci.org/browse/JENKINS-11286[JENKINS-11286]). The property should be set on the master and on all agents to have effect (see https://issues.jenkins-ci.org/browse/JENKINS-22547[JENKINS-22547]). [[GitPlugin-WhyNotJGit]] From ac3c1123e39ead54b1bb38168c0e2ae8415cee38 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Mon, 10 Feb 2020 06:02:39 -0700 Subject: [PATCH 063/101] Change truncation removed in 4.0, not 3.0 release Documentation error, change truncation was released in git plugin 4.0, not git plugin 3.0 --- README.adoc | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.adoc b/README.adoc index ebfea6b51e..6dd6663258 100644 --- a/README.adoc +++ b/README.adoc @@ -158,8 +158,8 @@ Create new accounts based on author/committer's email:: [[show-the-entire-commit-summary-in-changes]] Show the entire commit summary in changes:: - The `changes` page for each job would truncate the change summary prior to git plugin 3.0. - With the release of git plugin 3.0, the default was changed to show the complete change summary. + The `changes` page for each job would truncate the change summary prior to git plugin 4.0. + With the release of git plugin 4.0, the default was changed to show the complete change summary. Administrators that want to restore the old behavior may disable this setting. [#repository-browser] From 1b5d4985f273876d48488f42224e5dfcff00df07 Mon Sep 17 00:00:00 2001 From: steven-terrana Date: Wed, 12 Feb 2020 09:04:20 -0500 Subject: [PATCH 064/101] Update GitSCMFileSystem to be more generic by using prefix directly --- src/main/java/jenkins/plugins/git/GitSCMFileSystem.java | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java b/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java index ec9a2bc2b7..e93e373401 100644 --- a/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java +++ b/src/main/java/jenkins/plugins/git/GitSCMFileSystem.java @@ -332,10 +332,8 @@ public SCMFileSystem build(@NonNull Item owner, @NonNull SCM scm, @CheckForNull if (rev != null) { headName = rev.getHead().getName(); } else { - if (branchSpec.getName().startsWith(Constants.R_TAGS)){ - headName = branchSpec.getName().substring(Constants.R_TAGS.length()); - } else if (branchSpec.getName().startsWith(Constants.R_HEADS)) { - headName = branchSpec.getName().substring(Constants.R_HEADS.length()); + if (branchSpec.getName().startsWith(prefix)){ + headName = branchSpec.getName().substring(prefix.length()); } else if (branchSpec.getName().startsWith("*/")) { headName = branchSpec.getName().substring(2); } else { From 87478073494dd4991d9df7f6dd1a1f67aefc1763 Mon Sep 17 00:00:00 2001 From: steven-terrana Date: Sun, 16 Feb 2020 16:23:56 -0500 Subject: [PATCH 065/101] add unit test for creating SCMFileSystem from tag --- .../plugins/git/GitSCMFileSystemTest.java | 35 +++++++++++++++++++ 1 file changed, 35 insertions(+) diff --git a/src/test/java/jenkins/plugins/git/GitSCMFileSystemTest.java b/src/test/java/jenkins/plugins/git/GitSCMFileSystemTest.java index e74a0ce3c1..43bc73d841 100644 --- a/src/test/java/jenkins/plugins/git/GitSCMFileSystemTest.java +++ b/src/test/java/jenkins/plugins/git/GitSCMFileSystemTest.java @@ -351,6 +351,41 @@ public void given_filesystem_when_askingChangesSinceNewRevision_then_changesAreP assertThat(out.toString(), is("")); } + @Test + public void create_SCMFileSystem_from_tag() throws Exception { + sampleRepo.init(); + sampleRepo.git("checkout", "-b", "dev"); + sampleRepo.mkdirs("dir/subdir"); + sampleRepo.git("mv", "file", "dir/subdir/file"); + sampleRepo.write("dir/subdir/file", "modified"); + sampleRepo.git("commit", "--all", "--message=dev"); + sampleRepo.git("tag", "-a", "v1.0"); + SCMFileSystem fs = SCMFileSystem.of(r.createFreeStyleProject(), new GitSCM(GitSCM.createRepoList(sampleRepo.toString(), null), Collections.singletonList(new BranchSpec("refs/tags/v1.0")), false, Collections.emptyList(), null, null, Collections.emptyList())); + assertThat(fs, notNullValue()); + assertThat(fs.getRoot(), notNullValue()); + Iterable children = fs.getRoot().children(); + Iterator iterator = children.iterator(); + assertThat(iterator.hasNext(), is(true)); + SCMFile dir = iterator.next(); + assertThat(iterator.hasNext(), is(false)); + assertThat(dir.getName(), is("dir")); + assertThat(dir.getType(), is(SCMFile.Type.DIRECTORY)); + children = dir.children(); + iterator = children.iterator(); + assertThat(iterator.hasNext(), is(true)); + SCMFile subdir = iterator.next(); + assertThat(iterator.hasNext(), is(false)); + assertThat(subdir.getName(), is("subdir")); + assertThat(subdir.getType(), is(SCMFile.Type.DIRECTORY)); + children = subdir.children(); + iterator = children.iterator(); + assertThat(iterator.hasNext(), is(true)); + SCMFile file = iterator.next(); + assertThat(iterator.hasNext(), is(false)); + assertThat(file.getName(), is("file")); + assertThat(file.contentAsString(), is("modified")); + } + /** inline ${@link hudson.Functions#isWindows()} to prevent a transient remote classloader issue */ private boolean isWindows() { return java.io.File.pathSeparatorChar==';'; From 7d41af937061c4be3163ee23bfa50a2f113f61af Mon Sep 17 00:00:00 2001 From: steven-terrana Date: Sun, 16 Feb 2020 16:46:50 -0500 Subject: [PATCH 066/101] remediate errant test code --- src/test/java/jenkins/plugins/git/GitSCMFileSystemTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/java/jenkins/plugins/git/GitSCMFileSystemTest.java b/src/test/java/jenkins/plugins/git/GitSCMFileSystemTest.java index 43bc73d841..686ae5c334 100644 --- a/src/test/java/jenkins/plugins/git/GitSCMFileSystemTest.java +++ b/src/test/java/jenkins/plugins/git/GitSCMFileSystemTest.java @@ -359,7 +359,7 @@ public void create_SCMFileSystem_from_tag() throws Exception { sampleRepo.git("mv", "file", "dir/subdir/file"); sampleRepo.write("dir/subdir/file", "modified"); sampleRepo.git("commit", "--all", "--message=dev"); - sampleRepo.git("tag", "-a", "v1.0"); + sampleRepo.git("tag", "v1.0"); SCMFileSystem fs = SCMFileSystem.of(r.createFreeStyleProject(), new GitSCM(GitSCM.createRepoList(sampleRepo.toString(), null), Collections.singletonList(new BranchSpec("refs/tags/v1.0")), false, Collections.emptyList(), null, null, Collections.emptyList())); assertThat(fs, notNullValue()); assertThat(fs.getRoot(), notNullValue()); From f786e574ecf9d939456958830f2aed30023315c4 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 17 Feb 2020 08:17:40 +0000 Subject: [PATCH 067/101] Bump maven-checkstyle-plugin from 3.1.0 to 3.1.1 Bumps [maven-checkstyle-plugin](https://github.com/apache/maven-checkstyle-plugin) from 3.1.0 to 3.1.1. - [Release notes](https://github.com/apache/maven-checkstyle-plugin/releases) - [Commits](https://github.com/apache/maven-checkstyle-plugin/compare/maven-checkstyle-plugin-3.1.0...maven-checkstyle-plugin-3.1.1) Signed-off-by: dependabot-preview[bot] --- pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 5302f476b3..56d84bcea9 100644 --- a/pom.xml +++ b/pom.xml @@ -42,7 +42,7 @@ org.apache.maven.plugins maven-checkstyle-plugin - 3.1.0 + 3.1.1 google_checks.xml true From 503e0a3d9fb0053f3b6b3104b75cc3237eed7a44 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Thu, 20 Feb 2020 01:09:37 +0530 Subject: [PATCH 068/101] [JENKINS-48625] Restore binding of doCheckUrl methods and add some initial checks --- pom.xml | 11 +++ .../plugins/git/browser/AssemblaWeb.java | 72 +++++++++++----- .../git/browser/GitBlitRepositoryBrowser.java | 74 ++++++++++++----- .../hudson/plugins/git/browser/Gitiles.java | 73 +++++++++++----- .../plugins/git/browser/ViewGitWeb.java | 83 +++++++++++++------ .../hudson/plugins/git/Messages.properties | 1 + .../browser/AssemblaWebDoCheckURLTest.java | 63 ++++++++++++++ 7 files changed, 284 insertions(+), 93 deletions(-) create mode 100644 src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java diff --git a/pom.xml b/pom.xml index 5f2b8132e7..535a7575fe 100644 --- a/pom.xml +++ b/pom.xml @@ -255,6 +255,17 @@
    + + commons-validator + commons-validator + 1.6 + + + commons-digester + commons-digester + + + diff --git a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java index a6627fae84..8bcc70621c 100644 --- a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java +++ b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java @@ -1,15 +1,19 @@ package hudson.plugins.git.browser; import hudson.Extension; +import hudson.Util; import hudson.model.Descriptor; +import hudson.model.Item; import hudson.plugins.git.GitChangeSet; import hudson.plugins.git.GitChangeSet.Path; +import hudson.plugins.git.Messages; import hudson.scm.EditType; import hudson.scm.RepositoryBrowser; import hudson.util.FormValidation; import hudson.util.FormValidation.URLCheck; -import jenkins.model.Jenkins; +import org.apache.commons.validator.routines.UrlValidator; import net.sf.json.JSONObject; +import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.interceptor.RequirePOST; import org.kohsuke.stapler.QueryParameter; @@ -18,6 +22,8 @@ import javax.annotation.Nonnull; import javax.servlet.ServletException; import java.io.IOException; +import java.net.URI; +import java.net.URISyntaxException; import java.net.URL; /** @@ -94,33 +100,55 @@ public AssemblaWeb newInstance(StaplerRequest req, @Nonnull JSONObject jsonObjec } @RequirePOST - public FormValidation doCheckUrl(@QueryParameter(fixEmpty = true) final String url) - throws IOException, ServletException { - if (url == null) // nothing entered yet - { + public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParameter(fixEmpty = true) final String repoUrl) + throws IOException, ServletException, URISyntaxException { + + String cleanUrl = Util.fixEmptyAndTrim(repoUrl); + + if (cleanUrl == null) { return FormValidation.ok(); } - // Connect to URL and check content only if we have admin permission - if (!Jenkins.get().hasPermission(Jenkins.ADMINISTER)) + + if (project == null || !project.hasPermission(Item.CONFIGURE)) { return FormValidation.ok(); - return new URLCheck() { - protected FormValidation check() throws IOException, ServletException { - String v = url; - if (!v.endsWith("/")) { - v += '/'; - } + } + + if (cleanUrl.contains("$")) { + // set by variable, can't validate + return FormValidation.ok(); + } + FormValidation response; + if (checkURIFormat(cleanUrl)) { + return new URLCheck() { + protected FormValidation check() throws IOException, ServletException { + String v = cleanUrl; + if (!v.endsWith("/")) { + v += '/'; + } - try { - if (findText(open(new URL(v)), "Assembla")) { - return FormValidation.ok(); - } else { - return FormValidation.error("This is a valid URL but it doesn't look like Assembla"); + try { + if (findText(open(new URL(v)), "Assembla")) { + return FormValidation.ok(); + } else { + return FormValidation.error("This is a valid URL but it doesn't look like Assembla"); + } + } catch (IOException e) { + return handleIOException(v, e); } - } catch (IOException e) { - return handleIOException(v, e); } - } - }.check(); + }.check(); + } else { + response = FormValidation.error(Messages.invalidUrl()); + } + return response; + } + + private boolean checkURIFormat(String url) throws URISyntaxException { + //https://app.assembla.com/spaces/git-plugin/git/source + URI uri = new URI(url); + String[] schemes = {"http", "https"}; + UrlValidator urlValidator = new UrlValidator(schemes); + return urlValidator.isValid(uri.toString()) && uri.getHost().contains("assembla"); } } } diff --git a/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java index bfd8c4331b..2159b560f8 100644 --- a/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java @@ -1,15 +1,19 @@ package hudson.plugins.git.browser; import hudson.Extension; +import hudson.Util; import hudson.model.Descriptor; +import hudson.model.Item; import hudson.plugins.git.GitChangeSet; import hudson.plugins.git.GitChangeSet.Path; +import hudson.plugins.git.Messages; import hudson.scm.EditType; import hudson.scm.RepositoryBrowser; import hudson.util.FormValidation; import hudson.util.FormValidation.URLCheck; -import jenkins.model.Jenkins; import net.sf.json.JSONObject; +import org.apache.commons.validator.routines.UrlValidator; +import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.interceptor.RequirePOST; import org.kohsuke.stapler.QueryParameter; @@ -19,6 +23,8 @@ import javax.servlet.ServletException; import java.io.IOException; import java.io.UnsupportedEncodingException; +import java.net.URI; +import java.net.URISyntaxException; import java.net.URL; import java.net.URLEncoder; @@ -63,9 +69,10 @@ public String getProjectName() { return projectName; } - private String encodeString(final String s) throws UnsupportedEncodingException { + private String encodeString(final String s) throws UnsupportedEncodingException { return URLEncoder.encode(s, "UTF-8").replaceAll("\\+", "%20"); } + @Extension public static class ViewGitWebDescriptor extends Descriptor> { @Nonnull @@ -80,33 +87,54 @@ public GitBlitRepositoryBrowser newInstance(StaplerRequest req, @Nonnull JSONObj } @RequirePOST - public FormValidation doCheckUrl(@QueryParameter(fixEmpty = true) final String url) - throws IOException, ServletException { - if (url == null) // nothing entered yet - { + public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParameter(fixEmpty = true) final String repoUrl) + throws IOException, ServletException, URISyntaxException { + + String cleanUrl = Util.fixEmptyAndTrim(repoUrl); + + if (cleanUrl == null) { return FormValidation.ok(); } - // Connect to URL and check content only if we have admin permission - if (!Jenkins.get().hasPermission(Jenkins.ADMINISTER)) + + if (project == null || !project.hasPermission(Item.CONFIGURE)) { return FormValidation.ok(); - return new URLCheck() { - protected FormValidation check() throws IOException, ServletException { - String v = url; - if (!v.endsWith("/")) { - v += '/'; - } + } - try { - if (findText(open(new URL(v)), "Gitblit")) { - return FormValidation.ok(); - } else { - return FormValidation.error("This is a valid URL but it doesn't look like Gitblit"); + if (cleanUrl.contains("$")) { + // set by variable, can't validate + return FormValidation.ok(); + } + FormValidation response; + if (checkURIFormat(cleanUrl)) { + return new URLCheck() { + protected FormValidation check() throws IOException, ServletException { + String v = cleanUrl; + if (!v.endsWith("/")) { + v += '/'; + } + + try { + if (findText(open(new URL(v)), "Gitblit")) { + return FormValidation.ok(); + } else { + return FormValidation.error("This is a valid URL but it doesn't look like Gitblit"); + } + } catch (IOException e) { + return handleIOException(v, e); } - } catch (IOException e) { - return handleIOException(v, e); } - } - }.check(); + }.check(); + } else { + response = FormValidation.error(Messages.invalidUrl()); + } + return response; + } + + private boolean checkURIFormat(String url) throws URISyntaxException { + URI uri = new URI(url); + String[] schemes = {"http", "https"}; + UrlValidator urlValidator = new UrlValidator(schemes); + return urlValidator.isValid(uri.toString()) && uri.getHost().contains("gitblit"); } } } diff --git a/src/main/java/hudson/plugins/git/browser/Gitiles.java b/src/main/java/hudson/plugins/git/browser/Gitiles.java index 9768e4b1f2..d0cf57037e 100644 --- a/src/main/java/hudson/plugins/git/browser/Gitiles.java +++ b/src/main/java/hudson/plugins/git/browser/Gitiles.java @@ -1,16 +1,19 @@ package hudson.plugins.git.browser; import hudson.Extension; +import hudson.Util; import hudson.model.Descriptor; +import hudson.model.Item; import hudson.plugins.git.GitChangeSet; import hudson.plugins.git.GitChangeSet.Path; +import hudson.plugins.git.Messages; import hudson.scm.RepositoryBrowser; import hudson.util.FormValidation; import hudson.util.FormValidation.URLCheck; -import jenkins.model.Jenkins; - import java.io.IOException; +import java.net.URI; +import java.net.URISyntaxException; import java.net.URL; import javax.annotation.Nonnull; @@ -18,6 +21,8 @@ import net.sf.json.JSONObject; +import org.apache.commons.validator.routines.UrlValidator; +import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.interceptor.RequirePOST; import org.kohsuke.stapler.QueryParameter; @@ -70,30 +75,54 @@ public Gitiles newInstance(StaplerRequest req, @Nonnull JSONObject jsonObject) t } @RequirePOST - public FormValidation doCheckUrl(@QueryParameter(fixEmpty = true) final String url) throws IOException, ServletException { - if (url == null) // nothing entered yet + public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParameter(fixEmpty = true) final String repoUrl) + throws IOException, ServletException, URISyntaxException { + + String cleanUrl = Util.fixEmptyAndTrim(repoUrl); + + if (cleanUrl == null) { + return FormValidation.ok(); + } + + if (project == null || !project.hasPermission(Item.CONFIGURE)) { return FormValidation.ok(); - // Connect to URL and check content only if we have admin permission - if (!Jenkins.get().hasPermission(Jenkins.ADMINISTER)) + } + + if (cleanUrl.contains("$")) { + // set by variable, can't validate return FormValidation.ok(); - return new URLCheck() { - protected FormValidation check() throws IOException, ServletException { - String v = url; - if (!v.endsWith("/")) - v += '/'; - - try { - // gitiles has a line in main page indicating how to clone the project - if (findText(open(new URL(v)), "git clone")) { - return FormValidation.ok(); - } else { - return FormValidation.error("This is a valid URL but it doesn't look like Gitiles"); + } + FormValidation response; + if (checkURIFormat(cleanUrl)) { + return new URLCheck() { + protected FormValidation check() throws IOException, ServletException { + String v = cleanUrl; + if (!v.endsWith("/")) { + v += '/'; + } + + try { + if (findText(open(new URL(v)), "git clone")) { + return FormValidation.ok(); + } else { + return FormValidation.error("This is a valid URL but it doesn't look like Gitiles"); + } + } catch (IOException e) { + return handleIOException(v, e); } - } catch (IOException e) { - return handleIOException(v, e); } - } - }.check(); + }.check(); + } else { + response = FormValidation.error(Messages.invalidUrl()); + } + return response; + } + + private boolean checkURIFormat(String url) throws URISyntaxException { + URI uri = new URI(url); + String[] schemes = {"http", "https"}; + UrlValidator urlValidator = new UrlValidator(schemes); + return urlValidator.isValid(uri.toString()) && uri.getHost().contains("gerrit"); } } } diff --git a/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java b/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java index ad3c3cafa3..baa38c530c 100644 --- a/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java +++ b/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java @@ -1,16 +1,20 @@ package hudson.plugins.git.browser; import hudson.Extension; +import hudson.Util; import hudson.model.Descriptor; +import hudson.model.Item; import hudson.plugins.git.GitChangeSet; import hudson.plugins.git.GitChangeSet.Path; +import hudson.plugins.git.Messages; import hudson.scm.EditType; import hudson.scm.RepositoryBrowser; import hudson.scm.browsers.QueryBuilder; import hudson.util.FormValidation; import hudson.util.FormValidation.URLCheck; -import jenkins.model.Jenkins; import net.sf.json.JSONObject; +import org.apache.commons.validator.routines.UrlValidator; +import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.interceptor.RequirePOST; import org.kohsuke.stapler.QueryParameter; @@ -20,6 +24,8 @@ import javax.servlet.ServletException; import java.io.IOException; import java.io.UnsupportedEncodingException; +import java.net.URI; +import java.net.URISyntaxException; import java.net.URL; import java.net.URLEncoder; @@ -40,7 +46,7 @@ public URL getDiffLink(Path path) throws IOException { if (path.getEditType() == EditType.EDIT) { URL url = getUrl(); String spec = buildCommitDiffSpec(url, path); - return new URL(url, url.getPath() + spec); + return new URL(url, url.getPath() + spec); } return null; } @@ -52,14 +58,14 @@ public URL getFileLink(Path path) throws IOException { String spec = buildCommitDiffSpec(url, path); return encodeURL(new URL(url, url.getPath() + spec)); } - String spec = param(url).add("p=" + projectName).add("a=viewblob").add("h=" + path.getDst()).add("f=" + path.getPath()).toString(); + String spec = param(url).add("p=" + projectName).add("a=viewblob").add("h=" + path.getDst()).add("f=" + path.getPath()).toString(); return encodeURL(new URL(url, url.getPath() + spec)); } - private String buildCommitDiffSpec(URL url, Path path) - throws UnsupportedEncodingException { - return param(url).add("p=" + projectName).add("a=commitdiff").add("h=" + path.getChangeSet().getId()) + "#" + URLEncoder.encode(path.getPath(),"UTF-8").toString(); - } + private String buildCommitDiffSpec(URL url, Path path) + throws UnsupportedEncodingException { + return param(url).add("p=" + projectName).add("a=commitdiff").add("h=" + path.getChangeSet().getId()) + "#" + URLEncoder.encode(path.getPath(), "UTF-8").toString(); + } @Override public URL getChangeSetLink(GitChangeSet changeSet) throws IOException { @@ -89,29 +95,54 @@ public ViewGitWeb newInstance(StaplerRequest req, @Nonnull JSONObject jsonObject } @RequirePOST - public FormValidation doCheckUrl(@QueryParameter(fixEmpty = true) final String url) throws IOException, ServletException { - if (url == null) // nothing entered yet + public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParameter(fixEmpty = true) final String repoUrl) + throws IOException, ServletException, URISyntaxException { + + String cleanUrl = Util.fixEmptyAndTrim(repoUrl); + + if (cleanUrl == null) { + return FormValidation.ok(); + } + + if (project == null || !project.hasPermission(Item.CONFIGURE)) { return FormValidation.ok(); - // Connect to URL and check content only if we have admin permission - if (!Jenkins.get().hasPermission(Jenkins.ADMINISTER)) + } + + if (cleanUrl.contains("$")) { + // set by variable, can't validate return FormValidation.ok(); - return new URLCheck() { - protected FormValidation check() throws IOException, ServletException { - String v = url; - if (!v.endsWith("/")) - v += '/'; - - try { - if (findText(open(new URL(v)), "ViewGit")) { - return FormValidation.ok(); - } else { - return FormValidation.error("This is a valid URL but it doesn't look like ViewGit"); + } + FormValidation response; + if (checkURIFormat(cleanUrl)) { + return new URLCheck() { + protected FormValidation check() throws IOException, ServletException { + String v = cleanUrl; + if (!v.endsWith("/")) { + v += '/'; + } + + try { + if (findText(open(new URL(v)), "ViewGit")) { + return FormValidation.ok(); + } else { + return FormValidation.error("This is a valid URL but it doesn't look like ViewGit"); + } + } catch (IOException e) { + return handleIOException(v, e); } - } catch (IOException e) { - return handleIOException(v, e); } - } - }.check(); + }.check(); + } else { + response = FormValidation.error(Messages.invalidUrl()); + } + return response; + } + + private boolean checkURIFormat(String url) throws URISyntaxException { + URI uri = new URI(url); + String[] schemes = {"http", "https"}; + UrlValidator urlValidator = new UrlValidator(schemes); + return urlValidator.isValid(uri.toString()) && uri.getHost().contains("viewgit"); } } } diff --git a/src/main/resources/hudson/plugins/git/Messages.properties b/src/main/resources/hudson/plugins/git/Messages.properties index 11401f4bd1..f64069d344 100644 --- a/src/main/resources/hudson/plugins/git/Messages.properties +++ b/src/main/resources/hudson/plugins/git/Messages.properties @@ -6,6 +6,7 @@ BuildChooser_BuildingLastRevision=No new revisions were found; the most-recently UserRemoteConfig.FailedToConnect=Failed to connect to repository : {0} UserRemoteConfig.CheckUrl.UrlIsNull=Please enter Git repository. UserRemoteConfig.CheckRefSpec.InvalidRefSpec=Specification is invalid. +invalidUrl=Invalid URL GitPublisher.Check.TagName=Tag Name GitPublisher.Check.BranchName=Branch Name diff --git a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java new file mode 100644 index 0000000000..a7702d0e9c --- /dev/null +++ b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java @@ -0,0 +1,63 @@ +package hudson.plugins.git.browser; + +import hudson.model.FreeStyleProject; +import hudson.util.FormValidation; +import org.junit.Before; +import org.junit.Rule; +import org.junit.Test; +import org.jvnet.hudson.test.JenkinsRule; + + +import static org.junit.Assert.assertEquals; + +public class AssemblaWebDoCheckURLTest { + + @Rule + public JenkinsRule r = new JenkinsRule(); + + private FreeStyleProject project; + private AssemblaWeb.AssemblaWebDescriptor assemblaWebDescriptor; + + @Before + public void setProject() throws Exception { + project = r.createFreeStyleProject("p1"); + assemblaWebDescriptor = new AssemblaWeb.AssemblaWebDescriptor(); + } + + @Test + public void testInitialChecksOnRepoUrl() throws Exception { + String url = "https://app.assembla.com/spaces/git-plugin/git/source"; + // Empty url + String url2 = ""; + // URL with env variable + String url3 = "https://www.assembla.com/spaces/$"; + + assertEquals(FormValidation.ok(), assemblaWebDescriptor.doCheckRepoUrl(project, url)); + assertEquals(FormValidation.ok(), assemblaWebDescriptor.doCheckRepoUrl(project, url2)); + assertEquals(FormValidation.ok(), assemblaWebDescriptor.doCheckRepoUrl(project, url3)); + } + + @Test + public void testDomainLevelChecksOnRepoUrl() throws Exception { + // illegal syntax - Earlier it would open connection for such mistakes but now check resolves it beforehand. + String url = "https:/assembla.com"; + String url2 = "http//assmebla"; + + assertEquals("Invalid URL", assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage()); + assertEquals("Invalid URL", assemblaWebDescriptor.doCheckRepoUrl(project, url2).getLocalizedMessage()); + } + + @Test + public void testPathLevelChecksOnRepoUrl() throws Exception { + // Invalid path syntax + String url = "https://assembla.comspaces/git-plugin/git/source"; + // Syntax issue related specific to Assembla + String url2 = "https://app.assembla.com/space/git-plugin/git/source"; + // Any path related errors will not be caught except syntax issues + String url3 = "https://app.assembla.com/spaces"; + + assertEquals("Invalid URL", assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage()); + assertEquals("Unable to connect https://app.assembla.com/space/git-plugin/git/source/", assemblaWebDescriptor.doCheckRepoUrl(project, url2).getLocalizedMessage()); + assertEquals(FormValidation.ok(), assemblaWebDescriptor.doCheckRepoUrl(project, url3)); + } +} From f99b832e5a848714b5fdfc2a3881605c2c0163ba Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Wed, 19 Feb 2020 21:55:04 -0700 Subject: [PATCH 069/101] Proposed AssemblaWebTest changes --- .../plugins/git/browser/AssemblaWeb.java | 2 +- .../browser/AssemblaWebDoCheckURLTest.java | 76 +++++++++++++------ 2 files changed, 55 insertions(+), 23 deletions(-) diff --git a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java index 8bcc70621c..5d3a3e22bd 100644 --- a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java +++ b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java @@ -130,7 +130,7 @@ protected FormValidation check() throws IOException, ServletException { if (findText(open(new URL(v)), "Assembla")) { return FormValidation.ok(); } else { - return FormValidation.error("This is a valid URL but it doesn't look like Assembla"); + return FormValidation.error("This is a valid URL but it does not look like Assembla"); } } catch (IOException e) { return handleIOException(v, e); diff --git a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java index a7702d0e9c..39760276d1 100644 --- a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java +++ b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java @@ -3,61 +3,93 @@ import hudson.model.FreeStyleProject; import hudson.util.FormValidation; import org.junit.Before; -import org.junit.Rule; +import org.junit.ClassRule; import org.junit.Test; import org.jvnet.hudson.test.JenkinsRule; - -import static org.junit.Assert.assertEquals; +import static org.hamcrest.MatcherAssert.*; +import static org.hamcrest.Matchers.*; public class AssemblaWebDoCheckURLTest { - @Rule - public JenkinsRule r = new JenkinsRule(); + @ClassRule + public static JenkinsRule r = new JenkinsRule(); + private static int counter = 0; private FreeStyleProject project; private AssemblaWeb.AssemblaWebDescriptor assemblaWebDescriptor; @Before public void setProject() throws Exception { - project = r.createFreeStyleProject("p1"); + project = r.createFreeStyleProject("assembla-project-" + counter++); assemblaWebDescriptor = new AssemblaWeb.AssemblaWebDescriptor(); } @Test public void testInitialChecksOnRepoUrl() throws Exception { String url = "https://app.assembla.com/spaces/git-plugin/git/source"; - // Empty url - String url2 = ""; - // URL with env variable - String url3 = "https://www.assembla.com/spaces/$"; + assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url), is(FormValidation.ok())); + } + + @Test + public void testInitialChecksOnRepoUrlEmpty() throws Exception { + String url = ""; + assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url), is(FormValidation.ok())); + } - assertEquals(FormValidation.ok(), assemblaWebDescriptor.doCheckRepoUrl(project, url)); - assertEquals(FormValidation.ok(), assemblaWebDescriptor.doCheckRepoUrl(project, url2)); - assertEquals(FormValidation.ok(), assemblaWebDescriptor.doCheckRepoUrl(project, url3)); + @Test + public void testInitialChecksOnRepoUrlWithVariable() throws Exception { + String url = "https://www.assembla.com/spaces/$"; + assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url), is(FormValidation.ok())); } @Test public void testDomainLevelChecksOnRepoUrl() throws Exception { // illegal syntax - Earlier it would open connection for such mistakes but now check resolves it beforehand. String url = "https:/assembla.com"; - String url2 = "http//assmebla"; + assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage(), is("Invalid URL")); + } - assertEquals("Invalid URL", assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage()); - assertEquals("Invalid URL", assemblaWebDescriptor.doCheckRepoUrl(project, url2).getLocalizedMessage()); + @Test + public void testDomainLevelChecksOnRepoUrlInvalidURL() throws Exception { + // illegal syntax - Earlier it would open connection for such mistakes but now check resolves it beforehand. + String url = "http//assmebla"; + assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage(), is("Invalid URL")); } @Test - public void testPathLevelChecksOnRepoUrl() throws Exception { + public void testPathLevelChecksOnRepoUrlInvalidPathSyntax() throws Exception { // Invalid path syntax String url = "https://assembla.comspaces/git-plugin/git/source"; + assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage(), is("Invalid URL")); + } + + @Test + public void testPathLevelChecksOnRepoUrlValidURL() throws Exception { + // Syntax issue related specific to Assembla + String url = "https://app.assembla.com/space/git-plugin/git/source"; + assertThat(assemblaWebDescriptor.doCheckRepoUrl(null, url), is(FormValidation.ok())); + } + + @Test + public void testPathLevelChecksOnRepoUrlUnableToConnect() throws Exception { // Syntax issue related specific to Assembla - String url2 = "https://app.assembla.com/space/git-plugin/git/source"; + String url = "https://app.assembla.com/space/git-plugin/git/source"; + assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage(), + is("Unable to connect https://app.assembla.com/space/git-plugin/git/source/")); + } + + @Test + public void testPathLevelChecksOnRepoUrl() throws Exception { // Any path related errors will not be caught except syntax issues - String url3 = "https://app.assembla.com/spaces"; + String url = "https://app.assembla.com/spaces/"; + assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url), is(FormValidation.ok())); + } - assertEquals("Invalid URL", assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage()); - assertEquals("Unable to connect https://app.assembla.com/space/git-plugin/git/source/", assemblaWebDescriptor.doCheckRepoUrl(project, url2).getLocalizedMessage()); - assertEquals(FormValidation.ok(), assemblaWebDescriptor.doCheckRepoUrl(project, url3)); + @Test + public void testPathLevelChecksOnRepoUrlSupersetOfAssembla() throws Exception { + String url = "http://assemblagist.com/"; + assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage(), + is("This is a valid URL but it does not look like Assembla")); } } From a062e0bd38c3c5f04233c2e17767ee29626c930a Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 20 Feb 2020 08:48:50 -0700 Subject: [PATCH 070/101] Clarify comments for my benefit I had to read very carefully to detect the syntactic errors in the URL. The comment helps me see more clearly. --- .../plugins/git/browser/AssemblaWebDoCheckURLTest.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java index 39760276d1..4b4c970794 100644 --- a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java +++ b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java @@ -45,21 +45,21 @@ public void testInitialChecksOnRepoUrlWithVariable() throws Exception { @Test public void testDomainLevelChecksOnRepoUrl() throws Exception { - // illegal syntax - Earlier it would open connection for such mistakes but now check resolves it beforehand. + // Invalid URL, missing '/' character - Earlier it would open connection for such mistakes but now check resolves it beforehand. String url = "https:/assembla.com"; assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage(), is("Invalid URL")); } @Test public void testDomainLevelChecksOnRepoUrlInvalidURL() throws Exception { - // illegal syntax - Earlier it would open connection for such mistakes but now check resolves it beforehand. + // Invalid URL, missing ':' character - Earlier it would open connection for such mistakes but now check resolves it beforehand. String url = "http//assmebla"; assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage(), is("Invalid URL")); } @Test public void testPathLevelChecksOnRepoUrlInvalidPathSyntax() throws Exception { - // Invalid path syntax + // Invalid hostname in URL String url = "https://assembla.comspaces/git-plugin/git/source"; assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage(), is("Invalid URL")); } From c04b4a7289c414ee150621bd4f1fb45aec7193b0 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 20 Feb 2020 08:49:39 -0700 Subject: [PATCH 071/101] Extend null project test name to refer to null project --- .../hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java index 4b4c970794..e30d4b5a19 100644 --- a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java +++ b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java @@ -65,8 +65,7 @@ public void testPathLevelChecksOnRepoUrlInvalidPathSyntax() throws Exception { } @Test - public void testPathLevelChecksOnRepoUrlValidURL() throws Exception { - // Syntax issue related specific to Assembla + public void testPathLevelChecksOnRepoUrlValidURLNullProject() throws Exception { String url = "https://app.assembla.com/space/git-plugin/git/source"; assertThat(assemblaWebDescriptor.doCheckRepoUrl(null, url), is(FormValidation.ok())); } From 3a8d54917a609a9e8238c18fb5bcc131890187f2 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 20 Feb 2020 08:50:10 -0700 Subject: [PATCH 072/101] Test with a random URL that meets criteria Avoid undue load on any one server for this test. --- .../git/browser/AssemblaWebDoCheckURLTest.java | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java index e30d4b5a19..57a3c6e35f 100644 --- a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java +++ b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java @@ -87,7 +87,17 @@ public void testPathLevelChecksOnRepoUrl() throws Exception { @Test public void testPathLevelChecksOnRepoUrlSupersetOfAssembla() throws Exception { - String url = "http://assemblagist.com/"; + Random random = new Random(); + String [] urls = { + "http://assemblage.com/", + "http://assemblage.net/", + "http://assemblage.org/", + "http://assemblages.com/", + "http://assemblages.net/", + "http://assemblages.org/", + "http://assemblagist.com/", + }; + String url = urls[random.nextInt(urls.length)]; // Don't abuse a single web site with tests assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage(), is("This is a valid URL but it does not look like Assembla")); } From f29824937dc8a039eb6ca8b76f81d8c8c0812b7d Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 20 Feb 2020 09:22:55 -0700 Subject: [PATCH 073/101] Fix compile error on use of Random --- .../hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java index 57a3c6e35f..281bd9868e 100644 --- a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java +++ b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java @@ -87,7 +87,7 @@ public void testPathLevelChecksOnRepoUrl() throws Exception { @Test public void testPathLevelChecksOnRepoUrlSupersetOfAssembla() throws Exception { - Random random = new Random(); + java.util.Random random = new java.util.Random(); String [] urls = { "http://assemblage.com/", "http://assemblage.net/", From f62e1249c677b240a60d89741618f1d1885706c5 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Thu, 20 Feb 2020 09:35:31 -0700 Subject: [PATCH 074/101] Exclude jsoup from git plugin jpi packaging The jsoup jar file is added to the hpi file as a transitive dependency of the configuration as code test harness. The git plugin does not deliver the configuration as code test harness and so it should not deliver the dependencies of that test harness either. We've had issues in the past where other plugins mistakenly depended on a jar file that the git plugin bundled (like joda-time). Better to avoid others from depending on a transitive test dependency by not including the transitive test dependency. The jsoup jar file was included in git plugin 4.1.0 and 4.1.1. Earlier versions did not include it. https://github.com/jenkinsci/git-plugin/pull/814/commits/f3c65cb72548d3ab8ed863d5817624119b199455 added the transitive dependency. --- pom.xml | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/pom.xml b/pom.xml index 56d84bcea9..df17ddd7c0 100644 --- a/pom.xml +++ b/pom.xml @@ -242,6 +242,12 @@ test-harness ${configuration-as-code.version} test + + + org.jsoup + jsoup + + From 7293a3fa8f1a8f7b71d99b5e5ab4b4b0e26ca976 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Thu, 20 Feb 2020 23:11:42 +0530 Subject: [PATCH 075/101] initial checks and utility function is shifted to GitRepositoryBrowser class --- .../plugins/git/browser/AssemblaWeb.java | 24 ++----------------- .../git/browser/GitBlitRepositoryBrowser.java | 11 +-------- .../git/browser/GitRepositoryBrowser.java | 24 +++++++++++++++++++ .../hudson/plugins/git/browser/Gitiles.java | 23 ++---------------- .../plugins/git/browser/ViewGitWeb.java | 23 ++---------------- .../browser/AssemblaWebDoCheckURLTest.java | 2 +- 6 files changed, 32 insertions(+), 75 deletions(-) diff --git a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java index 5d3a3e22bd..4f3765f698 100644 --- a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java +++ b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java @@ -11,7 +11,6 @@ import hudson.scm.RepositoryBrowser; import hudson.util.FormValidation; import hudson.util.FormValidation.URLCheck; -import org.apache.commons.validator.routines.UrlValidator; import net.sf.json.JSONObject; import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; @@ -22,7 +21,6 @@ import javax.annotation.Nonnull; import javax.servlet.ServletException; import java.io.IOException; -import java.net.URI; import java.net.URISyntaxException; import java.net.URL; @@ -104,21 +102,11 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet throws IOException, ServletException, URISyntaxException { String cleanUrl = Util.fixEmptyAndTrim(repoUrl); - - if (cleanUrl == null) { - return FormValidation.ok(); - } - - if (project == null || !project.hasPermission(Item.CONFIGURE)) { - return FormValidation.ok(); - } - - if (cleanUrl.contains("$")) { - // set by variable, can't validate + if (initialChecksAndReturnOk(project, cleanUrl)) { return FormValidation.ok(); } FormValidation response; - if (checkURIFormat(cleanUrl)) { + if (checkURIFormat(cleanUrl, "assembla")) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { String v = cleanUrl; @@ -142,13 +130,5 @@ protected FormValidation check() throws IOException, ServletException { } return response; } - - private boolean checkURIFormat(String url) throws URISyntaxException { - //https://app.assembla.com/spaces/git-plugin/git/source - URI uri = new URI(url); - String[] schemes = {"http", "https"}; - UrlValidator urlValidator = new UrlValidator(schemes); - return urlValidator.isValid(uri.toString()) && uri.getHost().contains("assembla"); - } } } diff --git a/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java index 2159b560f8..cebc999cc5 100644 --- a/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java @@ -12,7 +12,6 @@ import hudson.util.FormValidation; import hudson.util.FormValidation.URLCheck; import net.sf.json.JSONObject; -import org.apache.commons.validator.routines.UrlValidator; import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.interceptor.RequirePOST; @@ -23,7 +22,6 @@ import javax.servlet.ServletException; import java.io.IOException; import java.io.UnsupportedEncodingException; -import java.net.URI; import java.net.URISyntaxException; import java.net.URL; import java.net.URLEncoder; @@ -105,7 +103,7 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet return FormValidation.ok(); } FormValidation response; - if (checkURIFormat(cleanUrl)) { + if (checkURIFormat(cleanUrl, "gitblit")) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { String v = cleanUrl; @@ -129,12 +127,5 @@ protected FormValidation check() throws IOException, ServletException { } return response; } - - private boolean checkURIFormat(String url) throws URISyntaxException { - URI uri = new URI(url); - String[] schemes = {"http", "https"}; - UrlValidator urlValidator = new UrlValidator(schemes); - return urlValidator.isValid(uri.toString()) && uri.getHost().contains("gitblit"); - } } } diff --git a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java index e23661756c..ece26ef44f 100644 --- a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java @@ -1,12 +1,14 @@ package hudson.plugins.git.browser; import hudson.EnvVars; +import hudson.model.Item; import hudson.model.Job; import hudson.model.TaskListener; import hudson.plugins.git.GitChangeSet; import hudson.plugins.git.GitChangeSet.Path; import hudson.scm.RepositoryBrowser; +import org.apache.commons.validator.routines.UrlValidator; import org.kohsuke.stapler.Stapler; import org.kohsuke.stapler.StaplerRequest; @@ -117,5 +119,27 @@ public static URL encodeURL(URL url) throws IOException { } } + public static boolean initialChecksAndReturnOk(Item project, String cleanUrl){ + if (cleanUrl == null) { + return true; + } + if (project == null || !project.hasPermission(Item.CONFIGURE)) { + return true; + } + if (cleanUrl.contains("$")) { + // set by variable, can't validate + return true; + } + return false; + } + + public static boolean checkURIFormat(String url, String browserName) throws URISyntaxException { + URI uri = new URI(url); + String[] schemes = {"http", "https"}; + UrlValidator urlValidator = new UrlValidator(schemes); + browserName = browserName + "."; + return urlValidator.isValid(uri.toString()) && uri.getHost().contains(browserName); + } + private static final long serialVersionUID = 1L; } diff --git a/src/main/java/hudson/plugins/git/browser/Gitiles.java b/src/main/java/hudson/plugins/git/browser/Gitiles.java index d0cf57037e..c8a92fba56 100644 --- a/src/main/java/hudson/plugins/git/browser/Gitiles.java +++ b/src/main/java/hudson/plugins/git/browser/Gitiles.java @@ -12,7 +12,6 @@ import hudson.util.FormValidation.URLCheck; import java.io.IOException; -import java.net.URI; import java.net.URISyntaxException; import java.net.URL; @@ -21,7 +20,6 @@ import net.sf.json.JSONObject; -import org.apache.commons.validator.routines.UrlValidator; import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.interceptor.RequirePOST; @@ -79,21 +77,11 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet throws IOException, ServletException, URISyntaxException { String cleanUrl = Util.fixEmptyAndTrim(repoUrl); - - if (cleanUrl == null) { - return FormValidation.ok(); - } - - if (project == null || !project.hasPermission(Item.CONFIGURE)) { - return FormValidation.ok(); - } - - if (cleanUrl.contains("$")) { - // set by variable, can't validate + if(initialChecksAndReturnOk(project, cleanUrl)){ return FormValidation.ok(); } FormValidation response; - if (checkURIFormat(cleanUrl)) { + if (checkURIFormat(cleanUrl, "gerrit")) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { String v = cleanUrl; @@ -117,12 +105,5 @@ protected FormValidation check() throws IOException, ServletException { } return response; } - - private boolean checkURIFormat(String url) throws URISyntaxException { - URI uri = new URI(url); - String[] schemes = {"http", "https"}; - UrlValidator urlValidator = new UrlValidator(schemes); - return urlValidator.isValid(uri.toString()) && uri.getHost().contains("gerrit"); - } } } diff --git a/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java b/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java index baa38c530c..b201810d46 100644 --- a/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java +++ b/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java @@ -13,7 +13,6 @@ import hudson.util.FormValidation; import hudson.util.FormValidation.URLCheck; import net.sf.json.JSONObject; -import org.apache.commons.validator.routines.UrlValidator; import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.interceptor.RequirePOST; @@ -24,7 +23,6 @@ import javax.servlet.ServletException; import java.io.IOException; import java.io.UnsupportedEncodingException; -import java.net.URI; import java.net.URISyntaxException; import java.net.URL; import java.net.URLEncoder; @@ -99,21 +97,11 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet throws IOException, ServletException, URISyntaxException { String cleanUrl = Util.fixEmptyAndTrim(repoUrl); - - if (cleanUrl == null) { - return FormValidation.ok(); - } - - if (project == null || !project.hasPermission(Item.CONFIGURE)) { - return FormValidation.ok(); - } - - if (cleanUrl.contains("$")) { - // set by variable, can't validate + if(initialChecksAndReturnOk(project, cleanUrl)){ return FormValidation.ok(); } FormValidation response; - if (checkURIFormat(cleanUrl)) { + if (checkURIFormat(cleanUrl, "viewgit")) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { String v = cleanUrl; @@ -137,12 +125,5 @@ protected FormValidation check() throws IOException, ServletException { } return response; } - - private boolean checkURIFormat(String url) throws URISyntaxException { - URI uri = new URI(url); - String[] schemes = {"http", "https"}; - UrlValidator urlValidator = new UrlValidator(schemes); - return urlValidator.isValid(uri.toString()) && uri.getHost().contains("viewgit"); - } } } diff --git a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java index 281bd9868e..9f51080885 100644 --- a/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java +++ b/src/test/java/hudson/plugins/git/browser/AssemblaWebDoCheckURLTest.java @@ -99,6 +99,6 @@ public void testPathLevelChecksOnRepoUrlSupersetOfAssembla() throws Exception { }; String url = urls[random.nextInt(urls.length)]; // Don't abuse a single web site with tests assertThat(assemblaWebDescriptor.doCheckRepoUrl(project, url).getLocalizedMessage(), - is("This is a valid URL but it does not look like Assembla")); + is("Invalid URL")); } } From 141c79f484fb2e18ee560c32c2fd6911ffee2b73 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Thu, 20 Feb 2020 23:51:46 +0530 Subject: [PATCH 076/101] Changed access modifier for utilities in GitRepositoryBrowser --- .../java/hudson/plugins/git/browser/GitRepositoryBrowser.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java index ece26ef44f..b3d6d92c86 100644 --- a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java @@ -119,7 +119,7 @@ public static URL encodeURL(URL url) throws IOException { } } - public static boolean initialChecksAndReturnOk(Item project, String cleanUrl){ + protected static boolean initialChecksAndReturnOk(Item project, String cleanUrl){ if (cleanUrl == null) { return true; } @@ -133,7 +133,7 @@ public static boolean initialChecksAndReturnOk(Item project, String cleanUrl){ return false; } - public static boolean checkURIFormat(String url, String browserName) throws URISyntaxException { + protected static boolean checkURIFormat(String url, String browserName) throws URISyntaxException { URI uri = new URI(url); String[] schemes = {"http", "https"}; UrlValidator urlValidator = new UrlValidator(schemes); From 454397e00aa243e9ccc3d65e38584620be6b5007 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 21 Feb 2020 10:47:19 +0530 Subject: [PATCH 077/101] change in checkURIFormat --- .../java/hudson/plugins/git/browser/AssemblaWeb.java | 12 +++++++++++- .../plugins/git/browser/GitRepositoryBrowser.java | 5 ++--- 2 files changed, 13 insertions(+), 4 deletions(-) diff --git a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java index 4f3765f698..b9d9899ac8 100644 --- a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java +++ b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java @@ -12,6 +12,7 @@ import hudson.util.FormValidation; import hudson.util.FormValidation.URLCheck; import net.sf.json.JSONObject; +import org.apache.commons.validator.routines.UrlValidator; import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.interceptor.RequirePOST; @@ -21,6 +22,7 @@ import javax.annotation.Nonnull; import javax.servlet.ServletException; import java.io.IOException; +import java.net.URI; import java.net.URISyntaxException; import java.net.URL; @@ -106,7 +108,7 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet return FormValidation.ok(); } FormValidation response; - if (checkURIFormat(cleanUrl, "assembla")) { + if (checkURIFormatAndHostName(cleanUrl, "assembla")) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { String v = cleanUrl; @@ -130,5 +132,13 @@ protected FormValidation check() throws IOException, ServletException { } return response; } + + private boolean checkURIFormatAndHostName(String url, String browserName) throws URISyntaxException { + URI uri = new URI(url); + String[] schemes = {"http", "https"}; + UrlValidator urlValidator = new UrlValidator(schemes); + browserName = browserName + "."; + return urlValidator.isValid(uri.toString()) && uri.getHost().contains(browserName); + } } } diff --git a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java index b3d6d92c86..d84e555e5d 100644 --- a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java @@ -133,12 +133,11 @@ protected static boolean initialChecksAndReturnOk(Item project, String cleanUrl) return false; } - protected static boolean checkURIFormat(String url, String browserName) throws URISyntaxException { + protected static boolean checkURIFormat(String url) throws URISyntaxException { URI uri = new URI(url); String[] schemes = {"http", "https"}; UrlValidator urlValidator = new UrlValidator(schemes); - browserName = browserName + "."; - return urlValidator.isValid(uri.toString()) && uri.getHost().contains(browserName); + return urlValidator.isValid(uri.toString()); } private static final long serialVersionUID = 1L; From 6532b346f68650902fcc90fa202a504bf9360ea9 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 21 Feb 2020 10:58:49 +0530 Subject: [PATCH 078/101] Revert "change in checkURIFormat" compile time errors corrected. This reverts commit 454397e00aa243e9ccc3d65e38584620be6b5007. --- .../java/hudson/plugins/git/browser/AssemblaWeb.java | 12 +----------- .../plugins/git/browser/GitRepositoryBrowser.java | 5 +++-- 2 files changed, 4 insertions(+), 13 deletions(-) diff --git a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java index b9d9899ac8..4f3765f698 100644 --- a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java +++ b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java @@ -12,7 +12,6 @@ import hudson.util.FormValidation; import hudson.util.FormValidation.URLCheck; import net.sf.json.JSONObject; -import org.apache.commons.validator.routines.UrlValidator; import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.interceptor.RequirePOST; @@ -22,7 +21,6 @@ import javax.annotation.Nonnull; import javax.servlet.ServletException; import java.io.IOException; -import java.net.URI; import java.net.URISyntaxException; import java.net.URL; @@ -108,7 +106,7 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet return FormValidation.ok(); } FormValidation response; - if (checkURIFormatAndHostName(cleanUrl, "assembla")) { + if (checkURIFormat(cleanUrl, "assembla")) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { String v = cleanUrl; @@ -132,13 +130,5 @@ protected FormValidation check() throws IOException, ServletException { } return response; } - - private boolean checkURIFormatAndHostName(String url, String browserName) throws URISyntaxException { - URI uri = new URI(url); - String[] schemes = {"http", "https"}; - UrlValidator urlValidator = new UrlValidator(schemes); - browserName = browserName + "."; - return urlValidator.isValid(uri.toString()) && uri.getHost().contains(browserName); - } } } diff --git a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java index d84e555e5d..b3d6d92c86 100644 --- a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java @@ -133,11 +133,12 @@ protected static boolean initialChecksAndReturnOk(Item project, String cleanUrl) return false; } - protected static boolean checkURIFormat(String url) throws URISyntaxException { + protected static boolean checkURIFormat(String url, String browserName) throws URISyntaxException { URI uri = new URI(url); String[] schemes = {"http", "https"}; UrlValidator urlValidator = new UrlValidator(schemes); - return urlValidator.isValid(uri.toString()); + browserName = browserName + "."; + return urlValidator.isValid(uri.toString()) && uri.getHost().contains(browserName); } private static final long serialVersionUID = 1L; From 4a0915a59a93402c934bab30a52636346a8a04d7 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 21 Feb 2020 11:03:57 +0530 Subject: [PATCH 079/101] Change in checkURIFormat and addition of checkURIFormatAndHostname in AssemblaWeb --- .../java/hudson/plugins/git/browser/AssemblaWeb.java | 12 +++++++++++- .../git/browser/GitBlitRepositoryBrowser.java | 2 +- .../plugins/git/browser/GitRepositoryBrowser.java | 5 ++--- .../java/hudson/plugins/git/browser/Gitiles.java | 2 +- .../java/hudson/plugins/git/browser/ViewGitWeb.java | 2 +- 5 files changed, 16 insertions(+), 7 deletions(-) diff --git a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java index 4f3765f698..b9d9899ac8 100644 --- a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java +++ b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java @@ -12,6 +12,7 @@ import hudson.util.FormValidation; import hudson.util.FormValidation.URLCheck; import net.sf.json.JSONObject; +import org.apache.commons.validator.routines.UrlValidator; import org.kohsuke.stapler.AncestorInPath; import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.interceptor.RequirePOST; @@ -21,6 +22,7 @@ import javax.annotation.Nonnull; import javax.servlet.ServletException; import java.io.IOException; +import java.net.URI; import java.net.URISyntaxException; import java.net.URL; @@ -106,7 +108,7 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet return FormValidation.ok(); } FormValidation response; - if (checkURIFormat(cleanUrl, "assembla")) { + if (checkURIFormatAndHostName(cleanUrl, "assembla")) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { String v = cleanUrl; @@ -130,5 +132,13 @@ protected FormValidation check() throws IOException, ServletException { } return response; } + + private boolean checkURIFormatAndHostName(String url, String browserName) throws URISyntaxException { + URI uri = new URI(url); + String[] schemes = {"http", "https"}; + UrlValidator urlValidator = new UrlValidator(schemes); + browserName = browserName + "."; + return urlValidator.isValid(uri.toString()) && uri.getHost().contains(browserName); + } } } diff --git a/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java index cebc999cc5..1e68369233 100644 --- a/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java @@ -103,7 +103,7 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet return FormValidation.ok(); } FormValidation response; - if (checkURIFormat(cleanUrl, "gitblit")) { + if (checkURIFormat(cleanUrl)) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { String v = cleanUrl; diff --git a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java index b3d6d92c86..d84e555e5d 100644 --- a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java @@ -133,12 +133,11 @@ protected static boolean initialChecksAndReturnOk(Item project, String cleanUrl) return false; } - protected static boolean checkURIFormat(String url, String browserName) throws URISyntaxException { + protected static boolean checkURIFormat(String url) throws URISyntaxException { URI uri = new URI(url); String[] schemes = {"http", "https"}; UrlValidator urlValidator = new UrlValidator(schemes); - browserName = browserName + "."; - return urlValidator.isValid(uri.toString()) && uri.getHost().contains(browserName); + return urlValidator.isValid(uri.toString()); } private static final long serialVersionUID = 1L; diff --git a/src/main/java/hudson/plugins/git/browser/Gitiles.java b/src/main/java/hudson/plugins/git/browser/Gitiles.java index c8a92fba56..b50eede513 100644 --- a/src/main/java/hudson/plugins/git/browser/Gitiles.java +++ b/src/main/java/hudson/plugins/git/browser/Gitiles.java @@ -81,7 +81,7 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet return FormValidation.ok(); } FormValidation response; - if (checkURIFormat(cleanUrl, "gerrit")) { + if (checkURIFormat(cleanUrl)) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { String v = cleanUrl; diff --git a/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java b/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java index b201810d46..971e92a954 100644 --- a/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java +++ b/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java @@ -101,7 +101,7 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet return FormValidation.ok(); } FormValidation response; - if (checkURIFormat(cleanUrl, "viewgit")) { + if (checkURIFormat(cleanUrl)) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { String v = cleanUrl; From 5f48308e825580e8f74e5d85997045a74504c081 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 21 Feb 2020 11:38:19 +0530 Subject: [PATCH 080/101] Removal of fixes of whitespace and temporary variable response --- .../plugins/git/browser/AssemblaWeb.java | 4 +--- .../git/browser/GitBlitRepositoryBrowser.java | 18 +++--------------- .../hudson/plugins/git/browser/Gitiles.java | 4 +--- .../hudson/plugins/git/browser/ViewGitWeb.java | 16 +++++++--------- 4 files changed, 12 insertions(+), 30 deletions(-) diff --git a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java index b9d9899ac8..cd0b0f26ef 100644 --- a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java +++ b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java @@ -107,7 +107,6 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet if (initialChecksAndReturnOk(project, cleanUrl)) { return FormValidation.ok(); } - FormValidation response; if (checkURIFormatAndHostName(cleanUrl, "assembla")) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { @@ -128,9 +127,8 @@ protected FormValidation check() throws IOException, ServletException { } }.check(); } else { - response = FormValidation.error(Messages.invalidUrl()); + return FormValidation.error(Messages.invalidUrl()); } - return response; } private boolean checkURIFormatAndHostName(String url, String browserName) throws URISyntaxException { diff --git a/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java index 1e68369233..e321dd4266 100644 --- a/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java @@ -67,7 +67,7 @@ public String getProjectName() { return projectName; } - private String encodeString(final String s) throws UnsupportedEncodingException { + private String encodeString(final String s) throws UnsupportedEncodingException { return URLEncoder.encode(s, "UTF-8").replaceAll("\\+", "%20"); } @@ -89,20 +89,9 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet throws IOException, ServletException, URISyntaxException { String cleanUrl = Util.fixEmptyAndTrim(repoUrl); - - if (cleanUrl == null) { - return FormValidation.ok(); - } - - if (project == null || !project.hasPermission(Item.CONFIGURE)) { - return FormValidation.ok(); - } - - if (cleanUrl.contains("$")) { - // set by variable, can't validate + if(initialChecksAndReturnOk(project, cleanUrl)){ return FormValidation.ok(); } - FormValidation response; if (checkURIFormat(cleanUrl)) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { @@ -123,9 +112,8 @@ protected FormValidation check() throws IOException, ServletException { } }.check(); } else { - response = FormValidation.error(Messages.invalidUrl()); + return FormValidation.error(Messages.invalidUrl()); } - return response; } } } diff --git a/src/main/java/hudson/plugins/git/browser/Gitiles.java b/src/main/java/hudson/plugins/git/browser/Gitiles.java index b50eede513..5e48172f24 100644 --- a/src/main/java/hudson/plugins/git/browser/Gitiles.java +++ b/src/main/java/hudson/plugins/git/browser/Gitiles.java @@ -80,7 +80,6 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet if(initialChecksAndReturnOk(project, cleanUrl)){ return FormValidation.ok(); } - FormValidation response; if (checkURIFormat(cleanUrl)) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { @@ -101,9 +100,8 @@ protected FormValidation check() throws IOException, ServletException { } }.check(); } else { - response = FormValidation.error(Messages.invalidUrl()); + return FormValidation.error(Messages.invalidUrl()); } - return response; } } } diff --git a/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java b/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java index 971e92a954..3a1ad3011e 100644 --- a/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java +++ b/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java @@ -44,7 +44,7 @@ public URL getDiffLink(Path path) throws IOException { if (path.getEditType() == EditType.EDIT) { URL url = getUrl(); String spec = buildCommitDiffSpec(url, path); - return new URL(url, url.getPath() + spec); + return new URL(url, url.getPath() + spec); } return null; } @@ -56,14 +56,14 @@ public URL getFileLink(Path path) throws IOException { String spec = buildCommitDiffSpec(url, path); return encodeURL(new URL(url, url.getPath() + spec)); } - String spec = param(url).add("p=" + projectName).add("a=viewblob").add("h=" + path.getDst()).add("f=" + path.getPath()).toString(); + String spec = param(url).add("p=" + projectName).add("a=viewblob").add("h=" + path.getDst()).add("f=" + path.getPath()).toString(); return encodeURL(new URL(url, url.getPath() + spec)); } - private String buildCommitDiffSpec(URL url, Path path) - throws UnsupportedEncodingException { - return param(url).add("p=" + projectName).add("a=commitdiff").add("h=" + path.getChangeSet().getId()) + "#" + URLEncoder.encode(path.getPath(), "UTF-8").toString(); - } + private String buildCommitDiffSpec(URL url, Path path) + throws UnsupportedEncodingException { + return param(url).add("p=" + projectName).add("a=commitdiff").add("h=" + path.getChangeSet().getId()) + "#" + URLEncoder.encode(path.getPath(), "UTF-8").toString(); + } @Override public URL getChangeSetLink(GitChangeSet changeSet) throws IOException { @@ -100,7 +100,6 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet if(initialChecksAndReturnOk(project, cleanUrl)){ return FormValidation.ok(); } - FormValidation response; if (checkURIFormat(cleanUrl)) { return new URLCheck() { protected FormValidation check() throws IOException, ServletException { @@ -121,9 +120,8 @@ protected FormValidation check() throws IOException, ServletException { } }.check(); } else { - response = FormValidation.error(Messages.invalidUrl()); + return FormValidation.error(Messages.invalidUrl()); } - return response; } } } From d6718012d2154c0478aba657a9a0ddb5667ea839 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Fri, 21 Feb 2020 09:10:58 -0700 Subject: [PATCH 081/101] Next release justifies 4.2.0 Includes tag support for SCM file system --- pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index df17ddd7c0..17309b31ad 100644 --- a/pom.xml +++ b/pom.xml @@ -26,7 +26,7 @@ 2007 - 4.1.2 + 4.2.0 -SNAPSHOT 2.138.4 8 From 122c6e93c91ed66b28d5e8c13b717e20fbdede45 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Fri, 21 Feb 2020 09:12:58 -0700 Subject: [PATCH 082/101] Remove javadoc warning --- src/main/java/hudson/plugins/git/UserRemoteConfig.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/hudson/plugins/git/UserRemoteConfig.java b/src/main/java/hudson/plugins/git/UserRemoteConfig.java index bbbd27f8d9..ab9abf07fc 100644 --- a/src/main/java/hudson/plugins/git/UserRemoteConfig.java +++ b/src/main/java/hudson/plugins/git/UserRemoteConfig.java @@ -221,7 +221,7 @@ public FormValidation doCheckUrl(@AncestorInPath Item item, * @param url Repository URL * @param value value of RefSpec * @return FormValidation.ok() or FormValidation.error() - * @throws IllegalArgumentException + * @throws IllegalArgumentException on unexpected argument error */ public FormValidation doCheckRefspec(@QueryParameter String name, @QueryParameter String url, From 8b1433ccfceea85827217f279cb0b06b35307d63 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sat, 29 Feb 2020 16:56:22 -0700 Subject: [PATCH 083/101] Revert CloneOptions change from a different branch Refspec expansion is handled in another pull request and should be evaluated separately. --- .../hudson/plugins/git/extensions/impl/CloneOption.java | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java b/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java index fb1bdf6933..be46f4339b 100644 --- a/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java +++ b/src/main/java/hudson/plugins/git/extensions/impl/CloneOption.java @@ -14,7 +14,6 @@ import hudson.plugins.git.util.GitUtils; import hudson.slaves.NodeProperty; import java.io.IOException; -import java.util.ArrayList; import java.util.List; import java.util.Objects; import org.eclipse.jgit.transport.RefSpec; @@ -149,12 +148,7 @@ public void decorateCloneCommand(GitSCM scm, Run build, GitClient git, Tas // in a single job definition. RemoteConfig rc = scm.getRepositories().get(0); List refspecs = rc.getFetchRefSpecs(); - List expandedRefSpecs = new ArrayList<>(); - EnvVars env = build.getEnvironment(listener); - for (RefSpec ref : refspecs) { - expandedRefSpecs.add(new RefSpec(env.expand(ref.toString()))); - } - cmd.refspecs(expandedRefSpecs); + cmd.refspecs(refspecs); } cmd.timeout(timeout); From acebb4689a095337b3196d5451e88ab6a5ec2909 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sat, 29 Feb 2020 16:58:27 -0700 Subject: [PATCH 084/101] Reduce whitespace differences from master branch --- .../plugins/git/browser/AssemblaWeb.java | 41 +++++++-------- .../git/browser/GitBlitRepositoryBrowser.java | 41 +++++++-------- .../git/browser/GitRepositoryBrowser.java | 3 +- .../hudson/plugins/git/browser/Gitiles.java | 39 +++++++-------- .../plugins/git/browser/ViewGitWeb.java | 50 +++++++++---------- 5 files changed, 86 insertions(+), 88 deletions(-) diff --git a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java index cd0b0f26ef..5c2622e771 100644 --- a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java +++ b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java @@ -104,31 +104,32 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet throws IOException, ServletException, URISyntaxException { String cleanUrl = Util.fixEmptyAndTrim(repoUrl); - if (initialChecksAndReturnOk(project, cleanUrl)) { + if (initialChecksAndReturnOk(project, cleanUrl)) + { return FormValidation.ok(); } - if (checkURIFormatAndHostName(cleanUrl, "assembla")) { - return new URLCheck() { - protected FormValidation check() throws IOException, ServletException { - String v = cleanUrl; - if (!v.endsWith("/")) { - v += '/'; - } + // Connect to URL and check content only if we have permission + if (!checkURIFormatAndHostName(cleanUrl, "assembla")) { + return FormValidation.error(Messages.invalidUrl()); + } + return new URLCheck() { + protected FormValidation check() throws IOException, ServletException { + String v = cleanUrl; + if (!v.endsWith("/")) { + v += '/'; + } - try { - if (findText(open(new URL(v)), "Assembla")) { - return FormValidation.ok(); - } else { - return FormValidation.error("This is a valid URL but it does not look like Assembla"); - } - } catch (IOException e) { - return handleIOException(v, e); + try { + if (findText(open(new URL(v)), "Assembla")) { + return FormValidation.ok(); + } else { + return FormValidation.error("This is a valid URL but it does not look like Assembla"); } + } catch (IOException e) { + return handleIOException(v, e); } - }.check(); - } else { - return FormValidation.error(Messages.invalidUrl()); - } + } + }.check(); } private boolean checkURIFormatAndHostName(String url, String browserName) throws URISyntaxException { diff --git a/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java index e321dd4266..5a4706a32f 100644 --- a/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitBlitRepositoryBrowser.java @@ -89,31 +89,32 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet throws IOException, ServletException, URISyntaxException { String cleanUrl = Util.fixEmptyAndTrim(repoUrl); - if(initialChecksAndReturnOk(project, cleanUrl)){ + if (initialChecksAndReturnOk(project, cleanUrl)) + { return FormValidation.ok(); } - if (checkURIFormat(cleanUrl)) { - return new URLCheck() { - protected FormValidation check() throws IOException, ServletException { - String v = cleanUrl; - if (!v.endsWith("/")) { - v += '/'; - } + if (!checkURIFormat(cleanUrl)) + { + return FormValidation.error(Messages.invalidUrl()); + } + return new URLCheck() { + protected FormValidation check() throws IOException, ServletException { + String v = cleanUrl; + if (!v.endsWith("/")) { + v += '/'; + } - try { - if (findText(open(new URL(v)), "Gitblit")) { - return FormValidation.ok(); - } else { - return FormValidation.error("This is a valid URL but it doesn't look like Gitblit"); - } - } catch (IOException e) { - return handleIOException(v, e); + try { + if (findText(open(new URL(v)), "Gitblit")) { + return FormValidation.ok(); + } else { + return FormValidation.error("This is a valid URL but it doesn't look like Gitblit"); } + } catch (IOException e) { + return handleIOException(v, e); } - }.check(); - } else { - return FormValidation.error(Messages.invalidUrl()); - } + } + }.check(); } } } diff --git a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java index d84e555e5d..b5b22d5a5d 100644 --- a/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/GitRepositoryBrowser.java @@ -134,10 +134,9 @@ protected static boolean initialChecksAndReturnOk(Item project, String cleanUrl) } protected static boolean checkURIFormat(String url) throws URISyntaxException { - URI uri = new URI(url); String[] schemes = {"http", "https"}; UrlValidator urlValidator = new UrlValidator(schemes); - return urlValidator.isValid(uri.toString()); + return urlValidator.isValid(url); } private static final long serialVersionUID = 1L; diff --git a/src/main/java/hudson/plugins/git/browser/Gitiles.java b/src/main/java/hudson/plugins/git/browser/Gitiles.java index 5e48172f24..acf32dbfa8 100644 --- a/src/main/java/hudson/plugins/git/browser/Gitiles.java +++ b/src/main/java/hudson/plugins/git/browser/Gitiles.java @@ -80,28 +80,27 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet if(initialChecksAndReturnOk(project, cleanUrl)){ return FormValidation.ok(); } - if (checkURIFormat(cleanUrl)) { - return new URLCheck() { - protected FormValidation check() throws IOException, ServletException { - String v = cleanUrl; - if (!v.endsWith("/")) { - v += '/'; - } - - try { - if (findText(open(new URL(v)), "git clone")) { - return FormValidation.ok(); - } else { - return FormValidation.error("This is a valid URL but it doesn't look like Gitiles"); - } - } catch (IOException e) { - return handleIOException(v, e); - } - } - }.check(); - } else { + if (!checkURIFormat(cleanUrl)) { return FormValidation.error(Messages.invalidUrl()); } + return new URLCheck() { + protected FormValidation check() throws IOException, ServletException { + String v = cleanUrl; + if (!v.endsWith("/")) + v += '/'; + + try { + // gitiles has a line in main page indicating how to clone the project + if (findText(open(new URL(v)), "git clone")) { + return FormValidation.ok(); + } else { + return FormValidation.error("This is a valid URL but it doesn't look like Gitiles"); + } + } catch (IOException e) { + return handleIOException(v, e); + } + } + }.check(); } } } diff --git a/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java b/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java index 3a1ad3011e..74234f8ea0 100644 --- a/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java +++ b/src/main/java/hudson/plugins/git/browser/ViewGitWeb.java @@ -44,7 +44,7 @@ public URL getDiffLink(Path path) throws IOException { if (path.getEditType() == EditType.EDIT) { URL url = getUrl(); String spec = buildCommitDiffSpec(url, path); - return new URL(url, url.getPath() + spec); + return new URL(url, url.getPath() + spec); } return null; } @@ -60,10 +60,10 @@ public URL getFileLink(Path path) throws IOException { return encodeURL(new URL(url, url.getPath() + spec)); } - private String buildCommitDiffSpec(URL url, Path path) - throws UnsupportedEncodingException { - return param(url).add("p=" + projectName).add("a=commitdiff").add("h=" + path.getChangeSet().getId()) + "#" + URLEncoder.encode(path.getPath(), "UTF-8").toString(); - } + private String buildCommitDiffSpec(URL url, Path path) + throws UnsupportedEncodingException { + return param(url).add("p=" + projectName).add("a=commitdiff").add("h=" + path.getChangeSet().getId()) + "#" + URLEncoder.encode(path.getPath(),"UTF-8").toString(); + } @Override public URL getChangeSetLink(GitChangeSet changeSet) throws IOException { @@ -97,31 +97,29 @@ public FormValidation doCheckRepoUrl(@AncestorInPath Item project, @QueryParamet throws IOException, ServletException, URISyntaxException { String cleanUrl = Util.fixEmptyAndTrim(repoUrl); - if(initialChecksAndReturnOk(project, cleanUrl)){ + // Connect to URL and check content only if we have admin permission + if (initialChecksAndReturnOk(project, cleanUrl)) return FormValidation.ok(); + if (!checkURIFormat(cleanUrl)) { + return FormValidation.error(Messages.invalidUrl()); } - if (checkURIFormat(cleanUrl)) { - return new URLCheck() { - protected FormValidation check() throws IOException, ServletException { - String v = cleanUrl; - if (!v.endsWith("/")) { - v += '/'; - } - - try { - if (findText(open(new URL(v)), "ViewGit")) { - return FormValidation.ok(); - } else { - return FormValidation.error("This is a valid URL but it doesn't look like ViewGit"); - } - } catch (IOException e) { - return handleIOException(v, e); + return new URLCheck() { + protected FormValidation check() throws IOException, ServletException { + String v = cleanUrl; + if (!v.endsWith("/")) + v += '/'; + + try { + if (findText(open(new URL(v)), "ViewGit")) { + return FormValidation.ok(); + } else { + return FormValidation.error("This is a valid URL but it doesn't look like ViewGit"); } + } catch (IOException e) { + return handleIOException(v, e); } - }.check(); - } else { - return FormValidation.error(Messages.invalidUrl()); - } + } + }.check(); } } } From d9fe71b6657ec3ab20fc5eaa7cf7896b035ba154 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sat, 29 Feb 2020 17:05:22 -0700 Subject: [PATCH 085/101] Better variable name in Assembla checker --- src/main/java/hudson/plugins/git/browser/AssemblaWeb.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java index 5c2622e771..aa05edf63b 100644 --- a/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java +++ b/src/main/java/hudson/plugins/git/browser/AssemblaWeb.java @@ -132,12 +132,12 @@ protected FormValidation check() throws IOException, ServletException { }.check(); } - private boolean checkURIFormatAndHostName(String url, String browserName) throws URISyntaxException { + private boolean checkURIFormatAndHostName(String url, String hostNameFragment) throws URISyntaxException { URI uri = new URI(url); String[] schemes = {"http", "https"}; UrlValidator urlValidator = new UrlValidator(schemes); - browserName = browserName + "."; - return urlValidator.isValid(uri.toString()) && uri.getHost().contains(browserName); + hostNameFragment = hostNameFragment + "."; + return urlValidator.isValid(uri.toString()) && uri.getHost().contains(hostNameFragment); } } } From ad01b82d517b33417d792d76b02206b28386766a Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sun, 1 Mar 2020 19:20:22 -0700 Subject: [PATCH 086/101] [maven-release-plugin] prepare release git-4.2.0 --- pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index 33b36731db..a7e5021f3d 100644 --- a/pom.xml +++ b/pom.xml @@ -17,7 +17,7 @@ git - ${revision}${changelist} + 4.2.0 hpi Jenkins Git plugin Integrates Jenkins with Git SCM @@ -290,7 +290,7 @@ scm:git:git://github.com/jenkinsci/${project.artifactId}-plugin.git scm:git:git@github.com:jenkinsci/${project.artifactId}-plugin.git https://github.com/jenkinsci/${project.artifactId}-plugin - ${scmTag} + git-4.2.0 From 996a83057e4efc49eb452e80c411f4078dddd77a Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Sun, 1 Mar 2020 19:20:31 -0700 Subject: [PATCH 087/101] [maven-release-plugin] prepare for next development iteration --- pom.xml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/pom.xml b/pom.xml index a7e5021f3d..bfcb4b5ac2 100644 --- a/pom.xml +++ b/pom.xml @@ -17,7 +17,7 @@ git - 4.2.0 + ${revision}${changelist} hpi Jenkins Git plugin Integrates Jenkins with Git SCM @@ -26,7 +26,7 @@ 2007 - 4.2.0 + 4.2.1 -SNAPSHOT 2.138.4 8 @@ -290,7 +290,7 @@ scm:git:git://github.com/jenkinsci/${project.artifactId}-plugin.git scm:git:git@github.com:jenkinsci/${project.artifactId}-plugin.git https://github.com/jenkinsci/${project.artifactId}-plugin - git-4.2.0 + ${scmTag} From c959c5d0c13e35899eb843fcea4f2e27dd52ea28 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 2 Mar 2020 08:55:38 +0000 Subject: [PATCH 088/101] Bump plugin from 3.56 to 3.57 Bumps [plugin](https://github.com/jenkinsci/plugin-pom) from 3.56 to 3.57. - [Release notes](https://github.com/jenkinsci/plugin-pom/releases) - [Changelog](https://github.com/jenkinsci/plugin-pom/blob/master/CHANGELOG.md) - [Commits](https://github.com/jenkinsci/plugin-pom/compare/plugin-3.56...plugin-3.57) Signed-off-by: dependabot-preview[bot] --- pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index bfcb4b5ac2..981c592d18 100644 --- a/pom.xml +++ b/pom.xml @@ -4,7 +4,7 @@ org.jenkins-ci.plugins plugin - 3.56 + 3.57 From f581998be38cfed8e080c672c4b7caa8b4a45979 Mon Sep 17 00:00:00 2001 From: Francisco Javier Fernandez Gonzalez Date: Tue, 3 Mar 2020 02:39:50 +0100 Subject: [PATCH 089/101] [SECURITY-1723] Co-authored-by: Daniel Beck --- .../browser/TFS2013GitRepositoryBrowser.java | 3 +- .../TFS2013GitRepositoryBrowserXSSTest.java | 48 +++++++++++++++++++ 2 files changed, 50 insertions(+), 1 deletion(-) create mode 100644 src/test/java/hudson/plugins/git/browser/TFS2013GitRepositoryBrowserXSSTest.java diff --git a/src/main/java/hudson/plugins/git/browser/TFS2013GitRepositoryBrowser.java b/src/main/java/hudson/plugins/git/browser/TFS2013GitRepositoryBrowser.java index 796945e1b1..12cc386c1e 100644 --- a/src/main/java/hudson/plugins/git/browser/TFS2013GitRepositoryBrowser.java +++ b/src/main/java/hudson/plugins/git/browser/TFS2013GitRepositoryBrowser.java @@ -1,6 +1,7 @@ package hudson.plugins.git.browser; import hudson.Extension; +import hudson.Util; import hudson.model.AbstractProject; import hudson.model.Descriptor; import hudson.plugins.git.GitChangeSet; @@ -123,7 +124,7 @@ public FormValidation doCheckRepoUrl(@QueryParameter(fixEmpty = true) String val GitSCM scm = (GitSCM) project.getScm(); RemoteConfig remote = scm.getRepositoryByName(value); if (remote == null) - return FormValidation.errorWithMarkup("There is no remote with the name " + value + ""); + return FormValidation.errorWithMarkup("There is no remote with the name " + Util.escape(value) + ""); value = remote.getURIs().get(0).toString(); } diff --git a/src/test/java/hudson/plugins/git/browser/TFS2013GitRepositoryBrowserXSSTest.java b/src/test/java/hudson/plugins/git/browser/TFS2013GitRepositoryBrowserXSSTest.java new file mode 100644 index 0000000000..f410aa1a70 --- /dev/null +++ b/src/test/java/hudson/plugins/git/browser/TFS2013GitRepositoryBrowserXSSTest.java @@ -0,0 +1,48 @@ +package hudson.plugins.git.browser; + +import com.gargoylesoftware.htmlunit.html.HtmlPage; +import hudson.model.FreeStyleProject; +import hudson.plugins.git.GitSCM; +import hudson.plugins.git.SubmoduleConfig; +import hudson.plugins.git.UserRemoteConfig; +import hudson.plugins.git.extensions.GitSCMExtension; +import org.jenkinsci.plugins.gitclient.JGitTool; +import org.junit.Assert; +import org.junit.Rule; +import org.junit.Test; +import org.jvnet.hudson.test.Issue; +import org.jvnet.hudson.test.JenkinsRule; + +import java.util.ArrayList; +import java.util.Collections; +import java.util.concurrent.atomic.AtomicBoolean; + +public class TFS2013GitRepositoryBrowserXSSTest { + + @Rule + public final JenkinsRule rule = new JenkinsRule(); + + @Test + @Issue("SECURITY-1723") + public void testXSS() throws Exception { + // setup scm + GitSCM scm = new GitSCM( + Collections.singletonList(new UserRemoteConfig("http://tfs/tfs/project/_git/repo", null, null, null)), + new ArrayList<>(), + false, Collections.emptyList(), + null, JGitTool.MAGIC_EXENAME, + Collections.emptyList()); + scm.setBrowser(new TFS2013GitRepositoryBrowser("")); + + FreeStyleProject p = rule.createFreeStyleProject(); + p.setScm(scm); + + AtomicBoolean xss = new AtomicBoolean(false); + JenkinsRule.WebClient wc = rule.createWebClient(); + wc.setAlertHandler((page, s) -> { + xss.set(true); + }); + HtmlPage page = wc.getPage(p, "configure"); + Assert.assertFalse(xss.get()); + } +} From c7af8c681d07ff043fe209fb1ba0c11f0cd5c4cc Mon Sep 17 00:00:00 2001 From: Daniel Beck Date: Tue, 3 Mar 2020 02:54:22 +0100 Subject: [PATCH 090/101] [maven-release-plugin] prepare release git-4.2.1 --- pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index bfcb4b5ac2..ee7ee14f5a 100644 --- a/pom.xml +++ b/pom.xml @@ -17,7 +17,7 @@ git - ${revision}${changelist} + 4.2.1 hpi Jenkins Git plugin Integrates Jenkins with Git SCM @@ -290,7 +290,7 @@ scm:git:git://github.com/jenkinsci/${project.artifactId}-plugin.git scm:git:git@github.com:jenkinsci/${project.artifactId}-plugin.git https://github.com/jenkinsci/${project.artifactId}-plugin - ${scmTag} + git-4.2.1 From a304e9835632d3524e3b8691964835d6f450a5f6 Mon Sep 17 00:00:00 2001 From: Daniel Beck Date: Tue, 3 Mar 2020 02:54:27 +0100 Subject: [PATCH 091/101] [maven-release-plugin] prepare for next development iteration --- pom.xml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/pom.xml b/pom.xml index ee7ee14f5a..02bae84348 100644 --- a/pom.xml +++ b/pom.xml @@ -17,7 +17,7 @@ git - 4.2.1 + ${revision}${changelist} hpi Jenkins Git plugin Integrates Jenkins with Git SCM @@ -26,7 +26,7 @@ 2007 - 4.2.1 + 4.2.2 -SNAPSHOT 2.138.4 8 @@ -290,7 +290,7 @@ scm:git:git://github.com/jenkinsci/${project.artifactId}-plugin.git scm:git:git@github.com:jenkinsci/${project.artifactId}-plugin.git https://github.com/jenkinsci/${project.artifactId}-plugin - git-4.2.1 + ${scmTag} From 5ae4d2abde2d08de9394b35536139bdf74b8a3a2 Mon Sep 17 00:00:00 2001 From: Mark Waite Date: Mon, 2 Mar 2020 22:01:23 -0700 Subject: [PATCH 092/101] Use simpler doc URL --- pom.xml | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index 981c592d18..98cb1f5b91 100644 --- a/pom.xml +++ b/pom.xml @@ -21,8 +21,7 @@ hpi Jenkins Git plugin Integrates Jenkins with Git SCM - - https://github.com/jenkinsci/${project.artifactId}-plugin/tree/${project.artifactId}-${revision}/README.adoc + https://github.com/jenkinsci/git-plugin/blob/master/README.adoc 2007 From 14e3c3e0060df13b155f6b738d75ad2eaa38a0b9 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 6 Mar 2020 03:12:04 +0530 Subject: [PATCH 093/101] Add UserIdentityTest --- .../git/extensions/impl/UserIdentityTest.java | 57 ++++++++++++++++++- 1 file changed, 56 insertions(+), 1 deletion(-) diff --git a/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java b/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java index c636a43ff6..549c987803 100644 --- a/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java +++ b/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java @@ -1,9 +1,64 @@ package hudson.plugins.git.extensions.impl; +import hudson.EnvVars; +import hudson.model.FreeStyleBuild; +import hudson.model.FreeStyleProject; +import hudson.model.Result; +import hudson.plugins.git.BranchSpec; +import hudson.plugins.git.GitSCM; +import hudson.plugins.git.TestGitRepo; +import hudson.plugins.git.UserRemoteConfig; +import hudson.plugins.git.extensions.GitSCMExtension; +import hudson.plugins.git.extensions.GitSCMExtensionTest; import nl.jqno.equalsverifier.EqualsVerifier; +import org.jenkinsci.plugins.gitclient.Git; +import org.jenkinsci.plugins.gitclient.GitClient; import org.junit.Test; -public class UserIdentityTest { +import java.util.ArrayList; +import java.util.Collections; +import java.util.List; + +import static org.hamcrest.MatcherAssert.assertThat; +import static org.hamcrest.Matchers.is; + +public class UserIdentityTest extends GitSCMExtensionTest { + + TestGitRepo repo; + GitClient git; + + @Override + public void before() throws Exception { + repo = new TestGitRepo("repo", tmp.newFolder(), listener); + git = Git.with(listener, new EnvVars()).in(repo.gitDir).getClient(); + } + + @Override + protected GitSCMExtension getExtension() { + return new UserIdentity("Jane Doe", "janeDoe@xyz.com"); + } + + @Test + public void testUserIdentity() throws Exception { + FreeStyleProject projectWithMaster = setupBasicProject(repo); + UserIdentity userIdentity = new UserIdentity("Jane Doe", "janeDoe@xyz.com"); + ((GitSCM)projectWithMaster.getScm()).getExtensions().add(userIdentity); + + git.commit("First commit"); + + FreeStyleBuild build = build(projectWithMaster, Result.SUCCESS); + EnvVars envVars = build.getEnvironment(listener); + assertThat("Jane Doe", is(envVars.get("GIT_AUTHOR_NAME"))); + assertThat("janeDoe@xyz.com", is(envVars.get("GIT_AUTHOR_EMAIL"))); + } + + @Test + public void testGetNameAndEmail(){ + UserIdentity userIdentity = new UserIdentity("Jane Doe", "janeDoe@xyz.com"); + + assertThat("Jane Doe", is(userIdentity.getName())); + assertThat("janeDoe@xyz.com", is(userIdentity.getEmail())); + } @Test public void equalsContract() { From 0a675bc45194171c027e7d7cc5f5a6994812aea6 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya <31189405+rishabhBudhouliya@users.noreply.github.com> Date: Fri, 6 Mar 2020 03:25:05 +0530 Subject: [PATCH 094/101] Update UserIdentityTest: Removed unnecessary imports --- .../plugins/git/extensions/impl/UserIdentityTest.java | 6 ------ 1 file changed, 6 deletions(-) diff --git a/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java b/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java index 549c987803..b95ead2fe0 100644 --- a/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java +++ b/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java @@ -4,10 +4,8 @@ import hudson.model.FreeStyleBuild; import hudson.model.FreeStyleProject; import hudson.model.Result; -import hudson.plugins.git.BranchSpec; import hudson.plugins.git.GitSCM; import hudson.plugins.git.TestGitRepo; -import hudson.plugins.git.UserRemoteConfig; import hudson.plugins.git.extensions.GitSCMExtension; import hudson.plugins.git.extensions.GitSCMExtensionTest; import nl.jqno.equalsverifier.EqualsVerifier; @@ -15,10 +13,6 @@ import org.jenkinsci.plugins.gitclient.GitClient; import org.junit.Test; -import java.util.ArrayList; -import java.util.Collections; -import java.util.List; - import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.Matchers.is; From 8d8cc36cf00c0fe8aa445476ca1b3d0dc32ed119 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 6 Mar 2020 13:20:18 +0530 Subject: [PATCH 095/101] Addition of unit test for WipeWorkspace and force clone extension behavior in GitSCM --- .../extensions/impl/WipeWorkspaceTest.java | 45 ++++++++++++++++++- 1 file changed, 44 insertions(+), 1 deletion(-) diff --git a/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java b/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java index 925518b546..971262b177 100644 --- a/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java +++ b/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java @@ -1,9 +1,52 @@ package hudson.plugins.git.extensions.impl; +import hudson.EnvVars; +import hudson.model.FreeStyleBuild; +import hudson.model.FreeStyleProject; +import hudson.model.Result; +import hudson.plugins.git.GitSCM; +import hudson.plugins.git.TestGitRepo; +import hudson.plugins.git.extensions.GitSCMExtension; +import hudson.plugins.git.extensions.GitSCMExtensionTest; import nl.jqno.equalsverifier.EqualsVerifier; +import org.jenkinsci.plugins.gitclient.Git; +import org.jenkinsci.plugins.gitclient.GitClient; import org.junit.Test; -public class WipeWorkspaceTest { +import static org.hamcrest.MatcherAssert.assertThat; +import static org.hamcrest.Matchers.is; + +public class WipeWorkspaceTest extends GitSCMExtensionTest { + + TestGitRepo repo; + GitClient git; + + @Override + public void before() throws Exception { + repo = new TestGitRepo("repo", tmp.newFolder(), listener); + git = Git.with(listener, new EnvVars()).in(repo.gitDir).getClient(); + } + + @Override + protected GitSCMExtension getExtension() { + return new WipeWorkspace(); + } + + /** + * Test to confirm the behavior of forcing re-clone before checkout by cleaning the workspace first. + **/ + @Test + public void testWipeWorkspace() throws Exception { + FreeStyleProject projectWithMaster = setupBasicProject(repo); + WipeWorkspace wipeWorkspaceExtension = new WipeWorkspace(); + ((GitSCM)projectWithMaster.getScm()).getExtensions().add(wipeWorkspaceExtension); + + git.commit("First commit"); + FreeStyleBuild build = build(projectWithMaster, Result.SUCCESS); + + String buildLog = build.getLog(); + assertThat("Workspace not cleaned before checkout",true, is(buildLog.contains("Wiping out workspace first."))); + } @Test public void equalsContract() { From 4cfc649b467fbf060d0dbf7b660769a2fd63601d Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 6 Mar 2020 21:58:19 +0530 Subject: [PATCH 096/101] Removed duplicate set extension in SCM line and added @WithoutJenkins for equalsContract --- .../plugins/git/extensions/impl/WipeWorkspaceTest.java | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java b/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java index 971262b177..6c78c0f5d7 100644 --- a/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java +++ b/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java @@ -4,7 +4,6 @@ import hudson.model.FreeStyleBuild; import hudson.model.FreeStyleProject; import hudson.model.Result; -import hudson.plugins.git.GitSCM; import hudson.plugins.git.TestGitRepo; import hudson.plugins.git.extensions.GitSCMExtension; import hudson.plugins.git.extensions.GitSCMExtensionTest; @@ -12,6 +11,7 @@ import org.jenkinsci.plugins.gitclient.Git; import org.jenkinsci.plugins.gitclient.GitClient; import org.junit.Test; +import org.jvnet.hudson.test.WithoutJenkins; import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.Matchers.is; @@ -38,9 +38,6 @@ protected GitSCMExtension getExtension() { @Test public void testWipeWorkspace() throws Exception { FreeStyleProject projectWithMaster = setupBasicProject(repo); - WipeWorkspace wipeWorkspaceExtension = new WipeWorkspace(); - ((GitSCM)projectWithMaster.getScm()).getExtensions().add(wipeWorkspaceExtension); - git.commit("First commit"); FreeStyleBuild build = build(projectWithMaster, Result.SUCCESS); @@ -49,6 +46,7 @@ public void testWipeWorkspace() throws Exception { } @Test + @WithoutJenkins public void equalsContract() { EqualsVerifier.forClass(WipeWorkspace.class) .usingGetClass() From 5f4f05b6bd9d8e7508382fd732fa26993a73b29f Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 6 Mar 2020 22:16:08 +0530 Subject: [PATCH 097/101] Removed duplicate code and added @WithoutJenkins --- .../git/extensions/impl/UserIdentityTest.java | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java b/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java index b95ead2fe0..8b0cd5e315 100644 --- a/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java +++ b/src/test/java/hudson/plugins/git/extensions/impl/UserIdentityTest.java @@ -4,7 +4,6 @@ import hudson.model.FreeStyleBuild; import hudson.model.FreeStyleProject; import hudson.model.Result; -import hudson.plugins.git.GitSCM; import hudson.plugins.git.TestGitRepo; import hudson.plugins.git.extensions.GitSCMExtension; import hudson.plugins.git.extensions.GitSCMExtensionTest; @@ -12,6 +11,7 @@ import org.jenkinsci.plugins.gitclient.Git; import org.jenkinsci.plugins.gitclient.GitClient; import org.junit.Test; +import org.jvnet.hudson.test.WithoutJenkins; import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.Matchers.is; @@ -22,9 +22,8 @@ public class UserIdentityTest extends GitSCMExtensionTest { GitClient git; @Override - public void before() throws Exception { - repo = new TestGitRepo("repo", tmp.newFolder(), listener); - git = Git.with(listener, new EnvVars()).in(repo.gitDir).getClient(); + public void before() { + // do nothing } @Override @@ -34,19 +33,20 @@ protected GitSCMExtension getExtension() { @Test public void testUserIdentity() throws Exception { - FreeStyleProject projectWithMaster = setupBasicProject(repo); - UserIdentity userIdentity = new UserIdentity("Jane Doe", "janeDoe@xyz.com"); - ((GitSCM)projectWithMaster.getScm()).getExtensions().add(userIdentity); + repo = new TestGitRepo("repo", tmp.newFolder(), listener); + git = Git.with(listener, new EnvVars()).in(repo.gitDir).getClient(); + FreeStyleProject projectWithMaster = setupBasicProject(repo); git.commit("First commit"); - FreeStyleBuild build = build(projectWithMaster, Result.SUCCESS); EnvVars envVars = build.getEnvironment(listener); + assertThat("Jane Doe", is(envVars.get("GIT_AUTHOR_NAME"))); assertThat("janeDoe@xyz.com", is(envVars.get("GIT_AUTHOR_EMAIL"))); } @Test + @WithoutJenkins public void testGetNameAndEmail(){ UserIdentity userIdentity = new UserIdentity("Jane Doe", "janeDoe@xyz.com"); @@ -55,6 +55,7 @@ public void testGetNameAndEmail(){ } @Test + @WithoutJenkins public void equalsContract() { EqualsVerifier.forClass(UserIdentity.class) .usingGetClass() From 0c41d45d8cb17fcd3bb67a6d5781ddfb874e69c0 Mon Sep 17 00:00:00 2001 From: Rishabh Budhouliya Date: Fri, 6 Mar 2020 22:22:24 +0530 Subject: [PATCH 098/101] A small change in before() method to run equalsContract() test --- .../plugins/git/extensions/impl/WipeWorkspaceTest.java | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java b/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java index 6c78c0f5d7..345d88c22d 100644 --- a/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java +++ b/src/test/java/hudson/plugins/git/extensions/impl/WipeWorkspaceTest.java @@ -23,8 +23,7 @@ public class WipeWorkspaceTest extends GitSCMExtensionTest { @Override public void before() throws Exception { - repo = new TestGitRepo("repo", tmp.newFolder(), listener); - git = Git.with(listener, new EnvVars()).in(repo.gitDir).getClient(); + // do nothing } @Override @@ -37,6 +36,9 @@ protected GitSCMExtension getExtension() { **/ @Test public void testWipeWorkspace() throws Exception { + repo = new TestGitRepo("repo", tmp.newFolder(), listener); + git = Git.with(listener, new EnvVars()).in(repo.gitDir).getClient(); + FreeStyleProject projectWithMaster = setupBasicProject(repo); git.commit("First commit"); FreeStyleBuild build = build(projectWithMaster, Result.SUCCESS); From 1ab4aa7e2dfc5d4a19eb9a67a7da53560410a902 Mon Sep 17 00:00:00 2001 From: "dependabot-preview[bot]" <27856297+dependabot-preview[bot]@users.noreply.github.com> Date: Mon, 9 Mar 2020 08:57:48 +0000 Subject: [PATCH 099/101] Bump xmlunit-matchers from 2.6.3 to 2.6.4 Bumps [xmlunit-matchers](https://github.com/xmlunit/xmlunit) from 2.6.3 to 2.6.4. - [Release notes](https://github.com/xmlunit/xmlunit/releases) - [Changelog](https://github.com/xmlunit/xmlunit/blob/master/RELEASE_NOTES.md) - [Commits](https://github.com/xmlunit/xmlunit/compare/v2.6.3...v2.6.4) Signed-off-by: dependabot-preview[bot] --- pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 98cb1f5b91..d918c769eb 100644 --- a/pom.xml +++ b/pom.xml @@ -214,7 +214,7 @@ org.xmlunit xmlunit-matchers - 2.6.3 + 2.6.4 test From 580f57853880192353c9e33adc01ee2f7224bac3 Mon Sep 17 00:00:00 2001 From: Francisco Javier Fernandez Gonzalez Date: Tue, 10 Mar 2020 13:53:56 +0100 Subject: [PATCH 100/101] [maven-release-plugin] prepare release git-4.2.2 --- pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index 6b2f394bce..1fe9edd6ae 100644 --- a/pom.xml +++ b/pom.xml @@ -17,7 +17,7 @@ git - ${revision}${changelist} + 4.2.2 hpi Jenkins Git plugin Integrates Jenkins with Git SCM @@ -289,7 +289,7 @@ scm:git:git://github.com/jenkinsci/${project.artifactId}-plugin.git scm:git:git@github.com:jenkinsci/${project.artifactId}-plugin.git https://github.com/jenkinsci/${project.artifactId}-plugin - ${scmTag} + git-4.2.2 From ead9a34ea0c3f27fbaf20caca0b9086e76aedb37 Mon Sep 17 00:00:00 2001 From: Francisco Javier Fernandez Gonzalez Date: Tue, 10 Mar 2020 13:54:09 +0100 Subject: [PATCH 101/101] [maven-release-plugin] prepare for next development iteration --- pom.xml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/pom.xml b/pom.xml index 1fe9edd6ae..d6946870fe 100644 --- a/pom.xml +++ b/pom.xml @@ -17,7 +17,7 @@ git - 4.2.2 + ${revision}${changelist} hpi Jenkins Git plugin Integrates Jenkins with Git SCM @@ -25,7 +25,7 @@ 2007 - 4.2.2 + 4.3.0 -SNAPSHOT 2.138.4 8 @@ -289,7 +289,7 @@ scm:git:git://github.com/jenkinsci/${project.artifactId}-plugin.git scm:git:git@github.com:jenkinsci/${project.artifactId}-plugin.git https://github.com/jenkinsci/${project.artifactId}-plugin - git-4.2.2 + ${scmTag}