From a13864be74b0bc8ce722f96c60a696342d72c5a5 Mon Sep 17 00:00:00 2001 From: Harald Albers Date: Thu, 14 Mar 2013 18:30:44 +0100 Subject: [PATCH 001/233] German translation for permission descriptions --- .../main/resources/hudson/Messages.properties | 2 +- .../resources/hudson/Messages_de.properties | 5 ++++ .../hudson/model/Messages.properties | 1 + .../hudson/model/Messages_de.properties | 23 +++++++++++++++++++ 4 files changed, 30 insertions(+), 1 deletion(-) diff --git a/core/src/main/resources/hudson/Messages.properties b/core/src/main/resources/hudson/Messages.properties index a90a3255d9..ccca534e2b 100644 --- a/core/src/main/resources/hudson/Messages.properties +++ b/core/src/main/resources/hudson/Messages.properties @@ -59,7 +59,7 @@ PluginManager.UploadPluginsPermission.Description=\ The "upload plugin" permission allows a user to upload arbitrary plugins. PluginManager.ConfigureUpdateCenterPermission.Description=\ The "configure update center" permission allows a user to \ -configure update sites and proxy settings. + configure update sites and proxy settings. AboutJenkins.DisplayName=About Jenkins AboutJenkins.Description=See the version and license information. diff --git a/core/src/main/resources/hudson/Messages_de.properties b/core/src/main/resources/hudson/Messages_de.properties index 42cf768def..ec3cd004be 100644 --- a/core/src/main/resources/hudson/Messages_de.properties +++ b/core/src/main/resources/hudson/Messages_de.properties @@ -49,5 +49,10 @@ Util.year ={0} {0,choice,0#Jahre|1#Jahr|1 Date: Tue, 19 Mar 2013 19:23:47 +0100 Subject: [PATCH 002/233] updated comment --- core/src/main/resources/hudson/model/Messages.properties | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/core/src/main/resources/hudson/model/Messages.properties b/core/src/main/resources/hudson/model/Messages.properties index 68538f6b0a..76df28d6cb 100644 --- a/core/src/main/resources/hudson/model/Messages.properties +++ b/core/src/main/resources/hudson/model/Messages.properties @@ -61,7 +61,8 @@ AbstractProject.DiscoverPermission.Description=\ This permission grants discover access to jobs. Lower than read permissions, it allows you to \ redirect anonymous users to the login page when they try to access a job url. \ Without it they would get a 404 error and wouldn't be able to discover project names. -# WipeOutPermission is only visible in security configuration if hudson.security.WipeOutPermission=true +# WipeOutPermission is only visible in the security configuration if the system property +# hudson.security.WipeOutPermission is set to true AbstractProject.WipeOutPermission.Description=\ This permission grants the ability to wipe out the contents of a workspace. AbstractProject.CancelPermission.Description=\ From d4459d9d0f99b951974f6ab1bedf6a580aad9248 Mon Sep 17 00:00:00 2001 From: redlab Date: Mon, 15 Apr 2013 20:59:06 +0200 Subject: [PATCH 003/233] As this is my first look inside Jenkins codebase I not sure it's correct but perhaps artifacts for modulebuilds should be deleted just as logs are deleted. see https://issues.jenkins-ci.org/browse/JENKINS-17508 I did not fully test it yet, all unit tests ran fine, but didn't succeed to run jobs inside Jenkins, due to classloader issues while running Jenkins in Jetty, to verify deletion --- .../src/main/java/hudson/maven/MavenModuleSetBuild.java | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/maven-plugin/src/main/java/hudson/maven/MavenModuleSetBuild.java b/maven-plugin/src/main/java/hudson/maven/MavenModuleSetBuild.java index c5874d3d61..6d34187435 100644 --- a/maven-plugin/src/main/java/hudson/maven/MavenModuleSetBuild.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenModuleSetBuild.java @@ -397,6 +397,14 @@ public class MavenModuleSetBuild extends AbstractMavenBuild list : getModuleBuilds().values()) + for (MavenBuild build : list) + build.deleteArtifacts(); + } + @Override public Object getDynamic(String token, StaplerRequest req, StaplerResponse rsp) { // map corresponding module build under this object From c8f73d0015365ab13a17c18ef8cd750cdcda2506 Mon Sep 17 00:00:00 2001 From: redlab Date: Wed, 17 Apr 2013 12:21:09 +0200 Subject: [PATCH 004/233] adds test that looks in jobs archive with 2 builds when LogRotator set as build discarder with settings to keep only 1 build with artifacts, test searches for jars in archive for build one and build two expecting no jars in build 1 and expecting jars in build 2 --- ...enMultiModuleLogRotatorCleanArtifacts.java | 78 +++++++++++++++++++ 1 file changed, 78 insertions(+) create mode 100644 test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java diff --git a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java new file mode 100644 index 0000000000..952efc8894 --- /dev/null +++ b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java @@ -0,0 +1,78 @@ +/** + * + */ +package hudson.maven; + +import hudson.FilePath; +import hudson.Launcher; +import hudson.maven.reporters.MavenFingerprinter; +import hudson.model.BuildListener; +import hudson.tasks.LogRotator; +import hudson.tasks.Maven.MavenInstallation; + +import java.io.File; +import java.io.IOException; +import java.net.URI; +import java.util.Collection; + +import org.apache.commons.io.FileUtils; +import org.apache.commons.io.filefilter.IOFileFilter; +import org.apache.commons.io.filefilter.PrefixFileFilter; +import org.junit.Assert; +import org.junit.BeforeClass; +import org.jvnet.hudson.test.ExtractResourceWithChangesSCM; +import org.jvnet.hudson.test.HudsonTestCase; + +/** + * @author redlab + * + */ +public class MavenMultiModuleLogRotatorCleanArtifacts extends HudsonTestCase { + + private MavenModuleSet m; + private FilePath jobs; + + private static class TestReporter extends MavenReporter { + @Override + public boolean end(MavenBuild build, Launcher launcher, + BuildListener listener) throws InterruptedException, + IOException { + assertNotNull(build.getProject().getWorkspace()); + assertNotNull(build.getWorkspace()); + return true; + } + } + @Override + protected void setUp() throws Exception { + super.setUp(); + configureDefaultMaven("apache-maven-2.2.1", MavenInstallation.MAVEN_21); + m = createMavenProject(); + m.setBuildDiscarder(new LogRotator("-1", "-1", "-1", "1")); + m.getReporters().add(new TestReporter()); + m.getReporters().add(new MavenFingerprinter()); + m.setScm(new ExtractResourceWithChangesSCM(getClass().getResource( + "maven-multimod.zip"), getClass().getResource( + "maven-multimod-changes.zip"))); + buildAndAssertSuccess(m); + // Now run a second build with the changes. + m.setIncrementalBuild(false); + buildAndAssertSuccess(m); + FilePath workspace = m.getWorkspace(); + URI uri = workspace.toURI(); + FilePath parent = workspace.getParent().getParent(); + jobs = new FilePath(parent, "jobs"); + } + + public void testArtifactsAreDeletedInBuildOneWhenBuildDiscarderRun() throws Exception { + File directory = new File(new FilePath(jobs, "test0/builds/1").toURI()); + System.out.println(directory); + Collection files = FileUtils.listFiles(directory, new String [] {"jar"}, true); + Assert.assertTrue("Found jars in previous build, that should not happen", files.isEmpty()); + Collection files2= FileUtils.listFiles(new File(new FilePath(jobs, "test0/builds/2").toURI()), new String [] {"jar"}, true); + Assert.assertFalse("No jars in last build ALERT!", files2.isEmpty()); + } + + + + +} From 2a0bd7eebd1ee70aa6099197f48810235ddc9ab0 Mon Sep 17 00:00:00 2001 From: redlab Date: Wed, 17 Apr 2013 14:02:46 +0200 Subject: [PATCH 005/233] add documentation to testcase. --- ...enMultiModuleLogRotatorCleanArtifacts.java | 24 +++++++++++++------ 1 file changed, 17 insertions(+), 7 deletions(-) diff --git a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java index 952efc8894..dbc7b8f5a2 100644 --- a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java +++ b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java @@ -20,10 +20,17 @@ import org.apache.commons.io.filefilter.IOFileFilter; import org.apache.commons.io.filefilter.PrefixFileFilter; import org.junit.Assert; import org.junit.BeforeClass; +import org.jvnet.hudson.test.Bug; import org.jvnet.hudson.test.ExtractResourceWithChangesSCM; import org.jvnet.hudson.test.HudsonTestCase; /** + * Testing https://issues.jenkins-ci.org/browse/JENKINS-17508
+ * test that looks in jobs archive with 2 builds when LogRotator set as build + * discarder with settings to keep only 1 build with artifacts, test searches + * for jars in archive for build one and build two, expecting no jars in build 1 + * and expecting jars in build 2 + * * @author redlab * */ @@ -42,6 +49,7 @@ public class MavenMultiModuleLogRotatorCleanArtifacts extends HudsonTestCase { return true; } } + @Override protected void setUp() throws Exception { super.setUp(); @@ -63,16 +71,18 @@ public class MavenMultiModuleLogRotatorCleanArtifacts extends HudsonTestCase { jobs = new FilePath(parent, "jobs"); } - public void testArtifactsAreDeletedInBuildOneWhenBuildDiscarderRun() throws Exception { + public void testArtifactsAreDeletedInBuildOneWhenBuildDiscarderRun() + throws Exception { File directory = new File(new FilePath(jobs, "test0/builds/1").toURI()); System.out.println(directory); - Collection files = FileUtils.listFiles(directory, new String [] {"jar"}, true); - Assert.assertTrue("Found jars in previous build, that should not happen", files.isEmpty()); - Collection files2= FileUtils.listFiles(new File(new FilePath(jobs, "test0/builds/2").toURI()), new String [] {"jar"}, true); + Collection files = FileUtils.listFiles(directory, + new String[] { "jar" }, true); + Assert.assertTrue( + "Found jars in previous build, that should not happen", + files.isEmpty()); + Collection files2 = FileUtils.listFiles(new File(new FilePath( + jobs, "test0/builds/2").toURI()), new String[] { "jar" }, true); Assert.assertFalse("No jars in last build ALERT!", files2.isEmpty()); } - - - } From ca7f4e682c8faa024053130d672d28684c010067 Mon Sep 17 00:00:00 2001 From: redlab Date: Thu, 18 Apr 2013 08:58:30 +0200 Subject: [PATCH 006/233] also testing the removal of build if LogRotator is configured to discard old builds and not only artifacts (Not needed for the issue, but an extra test is not a luxury ) --- ...enMultiModuleLogRotatorCleanArtifacts.java | 23 +++++++++++-------- 1 file changed, 14 insertions(+), 9 deletions(-) diff --git a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java index dbc7b8f5a2..6c8e877a1a 100644 --- a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java +++ b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java @@ -12,15 +12,10 @@ import hudson.tasks.Maven.MavenInstallation; import java.io.File; import java.io.IOException; -import java.net.URI; import java.util.Collection; import org.apache.commons.io.FileUtils; -import org.apache.commons.io.filefilter.IOFileFilter; -import org.apache.commons.io.filefilter.PrefixFileFilter; import org.junit.Assert; -import org.junit.BeforeClass; -import org.jvnet.hudson.test.Bug; import org.jvnet.hudson.test.ExtractResourceWithChangesSCM; import org.jvnet.hudson.test.HudsonTestCase; @@ -31,7 +26,6 @@ import org.jvnet.hudson.test.HudsonTestCase; * for jars in archive for build one and build two, expecting no jars in build 1 * and expecting jars in build 2 * - * @author redlab * */ public class MavenMultiModuleLogRotatorCleanArtifacts extends HudsonTestCase { @@ -55,7 +49,7 @@ public class MavenMultiModuleLogRotatorCleanArtifacts extends HudsonTestCase { super.setUp(); configureDefaultMaven("apache-maven-2.2.1", MavenInstallation.MAVEN_21); m = createMavenProject(); - m.setBuildDiscarder(new LogRotator("-1", "-1", "-1", "1")); + m.setBuildDiscarder(new LogRotator("-1", "2", "-1", "1")); m.getReporters().add(new TestReporter()); m.getReporters().add(new MavenFingerprinter()); m.setScm(new ExtractResourceWithChangesSCM(getClass().getResource( @@ -66,15 +60,14 @@ public class MavenMultiModuleLogRotatorCleanArtifacts extends HudsonTestCase { m.setIncrementalBuild(false); buildAndAssertSuccess(m); FilePath workspace = m.getWorkspace(); - URI uri = workspace.toURI(); FilePath parent = workspace.getParent().getParent(); jobs = new FilePath(parent, "jobs"); } + @SuppressWarnings("unchecked") public void testArtifactsAreDeletedInBuildOneWhenBuildDiscarderRun() throws Exception { File directory = new File(new FilePath(jobs, "test0/builds/1").toURI()); - System.out.println(directory); Collection files = FileUtils.listFiles(directory, new String[] { "jar" }, true); Assert.assertTrue( @@ -85,4 +78,16 @@ public class MavenMultiModuleLogRotatorCleanArtifacts extends HudsonTestCase { Assert.assertFalse("No jars in last build ALERT!", files2.isEmpty()); } + /** + * Performs a third build and expecting build one to be deleted + * @throws Exception + */ + @SuppressWarnings("unchecked") + public void testArtifactsOldBuildsDeletedWhenBuildDiscarderRun() + throws Exception { + buildAndAssertSuccess(m); + File directory = new File(new FilePath(jobs, "test0/builds/1").toURI()); + Assert.assertFalse("oops the build should have been deleted", directory.exists()); + } + } From 40cf543c4d400b28a161a6c11aa5b1aa98010e05 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sun, 21 Apr 2013 20:55:12 -0700 Subject: [PATCH 007/233] the trunk is toward 1.514-SNAPSHOT --- cli/pom.xml | 2 +- core/pom.xml | 2 +- maven-plugin/pom.xml | 2 +- plugins/pom.xml | 12 ++++++------ pom.xml | 2 +- test/pom.xml | 2 +- ui-samples-plugin/pom.xml | 2 +- war/pom.xml | 2 +- 8 files changed, 13 insertions(+), 13 deletions(-) diff --git a/cli/pom.xml b/cli/pom.xml index a6093d4fe4..1a5ff8a3bd 100644 --- a/cli/pom.xml +++ b/cli/pom.xml @@ -5,7 +5,7 @@ pom org.jenkins-ci.main - 1.513-SNAPSHOT + 1.514-SNAPSHOT cli diff --git a/core/pom.xml b/core/pom.xml index 982de84000..636d453829 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.513-SNAPSHOT + 1.514-SNAPSHOT ../pom.xml diff --git a/maven-plugin/pom.xml b/maven-plugin/pom.xml index bcbf221a68..3d2bf34dcf 100644 --- a/maven-plugin/pom.xml +++ b/maven-plugin/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.513-SNAPSHOT + 1.514-SNAPSHOT maven-plugin diff --git a/plugins/pom.xml b/plugins/pom.xml index 5fd983bb84..2cb7948fb8 100644 --- a/plugins/pom.xml +++ b/plugins/pom.xml @@ -11,7 +11,7 @@ org.jenkins-ci.plugins plugin Jenkins plugin POM - 1.513-SNAPSHOT + 1.514-SNAPSHOT pom org.jenkins-ci.main maven-plugin - 1.513-SNAPSHOT + 1.514-SNAPSHOT @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.513-SNAPSHOT + 1.514-SNAPSHOT test org.jenkins-ci.main jenkins-core - 1.513-SNAPSHOT + 1.514-SNAPSHOT provided org.jenkins-ci.main jenkins-test-harness - 1.513-SNAPSHOT + 1.514-SNAPSHOT test org.jenkins-ci.main ui-samples-plugin - 1.513-SNAPSHOT + 1.514-SNAPSHOT test diff --git a/core/src/main/java/jenkins/model/Jenkins.java b/core/src/main/java/jenkins/model/Jenkins.java index a5b6af1cb2..7ed3304bac 100755 --- a/core/src/main/java/jenkins/model/Jenkins.java +++ b/core/src/main/java/jenkins/model/Jenkins.java @@ -820,11 +820,13 @@ public class Jenkins extends AbstractCIBase implements ModifiableTopLevelItemGro } else tcpSlaveAgentListener = null; - try { - udpBroadcastThread = new UDPBroadcastThread(this); - udpBroadcastThread.start(); - } catch (IOException e) { - LOGGER.log(Level.WARNING, "Failed to broadcast over UDP",e); + if (UDPBroadcastThread.PORT != -1) { + try { + udpBroadcastThread = new UDPBroadcastThread(this); + udpBroadcastThread.start(); + } catch (IOException e) { + LOGGER.log(Level.WARNING, "Failed to broadcast over UDP (use -Dhudson.udp=-1 to disable)", e); + } } dnsMultiCast = new DNSMultiCast(this); From 64d27e9c4c73cd5cdd3e81c226bb8da23a42db6f Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 23 Apr 2013 13:26:55 -0400 Subject: [PATCH 010/233] =?UTF-8?q?Updated=20bundled=20plugins.=20Most=20n?= =?UTF-8?q?otable,=20cvs=201.6=20=E2=86=92=202.8,=20to=20get=20the=20criti?= =?UTF-8?q?cal=20fix=20of=20removing=20the=20mail=20address=20resolver.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- changelog.html | 2 ++ war/pom.xml | 16 ++++++++-------- 2 files changed, 10 insertions(+), 8 deletions(-) diff --git a/changelog.html b/changelog.html index bf3c578b65..570949eabb 100644 --- a/changelog.html +++ b/changelog.html @@ -57,6 +57,8 @@ Upcoming changes
  • Can use -Dhudson.udp=-1 to disable UDP broadcast without showing an ugly exception. +
  • + Updated bundled plugins.
diff --git a/war/pom.xml b/war/pom.xml index 824ee5ad54..4ae238f04c 100644 --- a/war/pom.xml +++ b/war/pom.xml @@ -270,43 +270,43 @@ THE SOFTWARE. org.jenkins-ci.plugins ssh-slaves - 0.23 + 0.25 hpi org.jenkins-ci.plugins credentials - 1.3.1 + 1.4 hpi org.jenkins-ci.plugins ssh-credentials - 0.2 + 0.3 hpi org.jenkins-ci.plugins subversion - 1.39 + 1.45 hpi org.jenkins-ci.plugins cvs - 1.6 + 2.8 hpi org.jenkins-ci.plugins ant - 1.1 + 1.2 hpi org.jenkins-ci.plugins javadoc - 1.0 + 1.1 hpi @@ -324,7 +324,7 @@ THE SOFTWARE. org.jenkins-ci.plugins ldap - 1.1 + 1.2 hpi From 13461b9359ff99e2e959a56fd8a82a79d2dddd1f Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 23 Apr 2013 13:53:56 -0400 Subject: [PATCH 011/233] /about now links to license information for plugins as well. --- changelog.html | 2 ++ .../resources/hudson/AboutJenkins/index.jelly | 17 +++++++++++++++++ .../hudson/AboutJenkins/index.properties | 3 ++- 3 files changed, 21 insertions(+), 1 deletion(-) diff --git a/changelog.html b/changelog.html index 570949eabb..e57d6028c1 100644 --- a/changelog.html +++ b/changelog.html @@ -57,6 +57,8 @@ Upcoming changes
  • Can use -Dhudson.udp=-1 to disable UDP broadcast without showing an ugly exception. +
  • + /about now links to license information for plugins as well.
  • Updated bundled plugins.
diff --git a/core/src/main/resources/hudson/AboutJenkins/index.jelly b/core/src/main/resources/hudson/AboutJenkins/index.jelly index ac9a036ee6..411d6e0ca4 100644 --- a/core/src/main/resources/hudson/AboutJenkins/index.jelly +++ b/core/src/main/resources/hudson/AboutJenkins/index.jelly @@ -38,6 +38,23 @@ THE SOFTWARE. +

${%plugin.dependencies}

+ diff --git a/core/src/main/resources/hudson/AboutJenkins/index.properties b/core/src/main/resources/hudson/AboutJenkins/index.properties index 08f9d8a0a8..907fcc70eb 100644 --- a/core/src/main/resources/hudson/AboutJenkins/index.properties +++ b/core/src/main/resources/hudson/AboutJenkins/index.properties @@ -23,4 +23,5 @@ about=About Jenkins {0} blurb=Jenkins is a community-developed open-source continuous integration server. -dependencies=Jenkins depends on the following 3rd party libraries. \ No newline at end of file +dependencies=Jenkins depends on the following 3rd party libraries. +plugin.dependencies=License and dependency information for plugins: From 0bf434845b5de755d730fb73ae1688b02dba8894 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 23 Apr 2013 14:46:47 -0400 Subject: [PATCH 012/233] [FIXED JENKINS-17724] /about was not showing licenses. A recent Stapler update caused the Jelly facet to ignore *.xml. So need to use raw j:include (as plugins were doing), not st:include (as core did). --- changelog.html | 3 +++ core/src/main/java/hudson/AboutJenkins.java | 9 +++++++++ .../main/resources/hudson/AboutJenkins/index.jelly | 14 +++++++++++--- 3 files changed, 23 insertions(+), 3 deletions(-) diff --git a/changelog.html b/changelog.html index e57d6028c1..456e5786b0 100644 --- a/changelog.html +++ b/changelog.html @@ -57,6 +57,9 @@ Upcoming changes
  • Can use -Dhudson.udp=-1 to disable UDP broadcast without showing an ugly exception. +
  • + Third-party license display for core was broken since 1.506. + (issue 17724)
  • /about now links to license information for plugins as well.
  • diff --git a/core/src/main/java/hudson/AboutJenkins.java b/core/src/main/java/hudson/AboutJenkins.java index e8136e1f5d..42332f9a92 100644 --- a/core/src/main/java/hudson/AboutJenkins.java +++ b/core/src/main/java/hudson/AboutJenkins.java @@ -1,6 +1,9 @@ package hudson; import hudson.model.ManagementLink; +import java.net.URL; +import org.kohsuke.accmod.Restricted; +import org.kohsuke.accmod.restrictions.NoExternalUse; /** * Show "About Jenkins" link. @@ -27,4 +30,10 @@ public class AboutJenkins extends ManagementLink { public String getDescription() { return Messages.AboutJenkins_Description(); } + + @Restricted(NoExternalUse.class) + public URL getLicensesURL() { + return AboutJenkins.class.getResource("/META-INF/licenses.xml"); + } + } diff --git a/core/src/main/resources/hudson/AboutJenkins/index.jelly b/core/src/main/resources/hudson/AboutJenkins/index.jelly index 411d6e0ca4..4b4a5ba458 100644 --- a/core/src/main/resources/hudson/AboutJenkins/index.jelly +++ b/core/src/main/resources/hudson/AboutJenkins/index.jelly @@ -35,9 +35,17 @@ THE SOFTWARE.

    ${%dependencies}

    - - - + + + + + + + + +

    ${%No information recorded}

    +
    +

    ${%plugin.dependencies}

      From aa1d28b04014c18838e87b3a8b1707cc5eb28b14 Mon Sep 17 00:00:00 2001 From: redlab Date: Tue, 23 Apr 2013 21:09:24 +0200 Subject: [PATCH 013/233] JENKINS-17508 updated the test to use @Rule and no longer extend from the old HudsonTestCase (shouldn't that one be marked deprecated?), add @ Bug and @ For as jesse suggested --- ...tiModuleLogRotatorCleanArtifactsTest.java} | 43 +++++++++++++------ 1 file changed, 29 insertions(+), 14 deletions(-) rename test/src/test/java/hudson/maven/{MavenMultiModuleLogRotatorCleanArtifacts.java => MavenMultiModuleLogRotatorCleanArtifactsTest.java} (76%) diff --git a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java similarity index 76% rename from test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java rename to test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java index 6c8e877a1a..4842ee3f63 100644 --- a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifacts.java +++ b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java @@ -16,8 +16,13 @@ import java.util.Collection; import org.apache.commons.io.FileUtils; import org.junit.Assert; +import org.junit.Before; +import org.junit.Rule; +import org.junit.Test; +import org.jvnet.hudson.test.Bug; import org.jvnet.hudson.test.ExtractResourceWithChangesSCM; -import org.jvnet.hudson.test.HudsonTestCase; +import org.jvnet.hudson.test.For; +import org.jvnet.hudson.test.JenkinsRule; /** * Testing https://issues.jenkins-ci.org/browse/JENKINS-17508
      @@ -28,42 +33,52 @@ import org.jvnet.hudson.test.HudsonTestCase; * * */ -public class MavenMultiModuleLogRotatorCleanArtifacts extends HudsonTestCase { +public class MavenMultiModuleLogRotatorCleanArtifactsTest { + + @Rule + public JenkinsRule j = new JenkinsRule(); private MavenModuleSet m; private FilePath jobs; private static class TestReporter extends MavenReporter { + /** + * + */ + private static final long serialVersionUID = 1L; + @Override public boolean end(MavenBuild build, Launcher launcher, BuildListener listener) throws InterruptedException, IOException { - assertNotNull(build.getProject().getWorkspace()); - assertNotNull(build.getWorkspace()); + Assert.assertNotNull(build.getProject().getWorkspace()); + Assert.assertNotNull(build.getWorkspace()); return true; } } - @Override - protected void setUp() throws Exception { - super.setUp(); - configureDefaultMaven("apache-maven-2.2.1", MavenInstallation.MAVEN_21); - m = createMavenProject(); + @Before + public void setUp() throws Exception { + j.configureDefaultMaven("apache-maven-2.2.1", MavenInstallation.MAVEN_21); + m = j.createMavenProject(); m.setBuildDiscarder(new LogRotator("-1", "2", "-1", "1")); m.getReporters().add(new TestReporter()); m.getReporters().add(new MavenFingerprinter()); m.setScm(new ExtractResourceWithChangesSCM(getClass().getResource( "maven-multimod.zip"), getClass().getResource( "maven-multimod-changes.zip"))); - buildAndAssertSuccess(m); + j.buildAndAssertSuccess(m); // Now run a second build with the changes. m.setIncrementalBuild(false); - buildAndAssertSuccess(m); + j.buildAndAssertSuccess(m); FilePath workspace = m.getWorkspace(); FilePath parent = workspace.getParent().getParent(); jobs = new FilePath(parent, "jobs"); } - + + @Test + @Bug(17508) + @For(MavenModuleSetBuild.class) @SuppressWarnings("unchecked") public void testArtifactsAreDeletedInBuildOneWhenBuildDiscarderRun() throws Exception { @@ -82,10 +97,10 @@ public class MavenMultiModuleLogRotatorCleanArtifacts extends HudsonTestCase { * Performs a third build and expecting build one to be deleted * @throws Exception */ - @SuppressWarnings("unchecked") + @Test public void testArtifactsOldBuildsDeletedWhenBuildDiscarderRun() throws Exception { - buildAndAssertSuccess(m); + j.buildAndAssertSuccess(m); File directory = new File(new FilePath(jobs, "test0/builds/1").toURI()); Assert.assertFalse("oops the build should have been deleted", directory.exists()); } From cd599817b365d08587c8e353c5516862d698d8ec Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 23 Apr 2013 17:36:08 -0400 Subject: [PATCH 014/233] Upgraded test deps on ant and subversion plugins. --- test/pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/pom.xml b/test/pom.xml index 61d02ccaeb..0de6173953 100644 --- a/test/pom.xml +++ b/test/pom.xml @@ -69,12 +69,12 @@ THE SOFTWARE. org.jenkins-ci.plugins ant - 1.1 + 1.2 org.jenkins-ci.plugins subversion - 1.26 + 1.45 org.jenkins-ci.plugins From 06e459fffebfe447dcd3edad73559ffb4a8ae707 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 23 Apr 2013 20:21:01 -0400 Subject: [PATCH 015/233] [FIXED JENKINS-17728] ParentBuildAction.parent can sometimes be null. --- changelog.html | 3 +++ core/src/main/java/hudson/matrix/MatrixConfiguration.java | 5 ++++- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/changelog.html b/changelog.html index 456e5786b0..e3949d2bc5 100644 --- a/changelog.html +++ b/changelog.html @@ -60,6 +60,9 @@ Upcoming changes
    • Third-party license display for core was broken since 1.506. (issue 17724) +
    • + NPE from MatrixConfiguration.newBuild. + (issue 17728)
    • /about now links to license information for plugins as well.
    • diff --git a/core/src/main/java/hudson/matrix/MatrixConfiguration.java b/core/src/main/java/hudson/matrix/MatrixConfiguration.java index 66516a0e33..b1c56409be 100644 --- a/core/src/main/java/hudson/matrix/MatrixConfiguration.java +++ b/core/src/main/java/hudson/matrix/MatrixConfiguration.java @@ -232,7 +232,10 @@ public class MatrixConfiguration extends Project MatrixBuild lb = getParent().getLastBuild(); for (Action a : actions) { if (a instanceof ParentBuildAction) { - lb = ((ParentBuildAction) a).parent; + MatrixBuild _lb = ((ParentBuildAction) a).parent; + if (_lb != null) { + lb = _lb; + } } } From f9ce6558c93d7f7ff0f8df12fb80f9ecc868ff99 Mon Sep 17 00:00:00 2001 From: redlab Date: Wed, 24 Apr 2013 10:54:42 +0200 Subject: [PATCH 016/233] JENKINS-17508 removed usage of deprecated elements in test --- ...avenMultiModuleLogRotatorCleanArtifactsTest.java | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java index 4842ee3f63..8b4b943935 100644 --- a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java +++ b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java @@ -25,11 +25,11 @@ import org.jvnet.hudson.test.For; import org.jvnet.hudson.test.JenkinsRule; /** - * Testing https://issues.jenkins-ci.org/browse/JENKINS-17508
      - * test that looks in jobs archive with 2 builds when LogRotator set as build + * + * Test that looks in jobs archive with 2 builds. When LogRotator set as build * discarder with settings to keep only 1 build with artifacts, test searches * for jars in archive for build one and build two, expecting no jars in build 1 - * and expecting jars in build 2 + * and expecting jars in build 2. * * */ @@ -51,7 +51,7 @@ public class MavenMultiModuleLogRotatorCleanArtifactsTest { public boolean end(MavenBuild build, Launcher launcher, BuildListener listener) throws InterruptedException, IOException { - Assert.assertNotNull(build.getProject().getWorkspace()); + Assert.assertNotNull(build.getProject().getSomeWorkspace()); Assert.assertNotNull(build.getWorkspace()); return true; } @@ -71,14 +71,14 @@ public class MavenMultiModuleLogRotatorCleanArtifactsTest { // Now run a second build with the changes. m.setIncrementalBuild(false); j.buildAndAssertSuccess(m); - FilePath workspace = m.getWorkspace(); + FilePath workspace = m.getSomeWorkspace(); FilePath parent = workspace.getParent().getParent(); jobs = new FilePath(parent, "jobs"); } @Test @Bug(17508) - @For(MavenModuleSetBuild.class) + @For({MavenModuleSetBuild.class, LogRotator.class}) @SuppressWarnings("unchecked") public void testArtifactsAreDeletedInBuildOneWhenBuildDiscarderRun() throws Exception { @@ -97,6 +97,7 @@ public class MavenMultiModuleLogRotatorCleanArtifactsTest { * Performs a third build and expecting build one to be deleted * @throws Exception */ + @For({MavenModuleSetBuild.class, LogRotator.class}) @Test public void testArtifactsOldBuildsDeletedWhenBuildDiscarderRun() throws Exception { From 33c8ac4d185264ba68b1c036c2daad5a51cd06aa Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Wed, 24 Apr 2013 11:03:51 -0700 Subject: [PATCH 017/233] this shouldn't be quoted --- core/src/main/resources/lib/layout/copyButton/copyButton.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/main/resources/lib/layout/copyButton/copyButton.js b/core/src/main/resources/lib/layout/copyButton/copyButton.js index c3eff55702..6e5283952a 100644 --- a/core/src/main/resources/lib/layout/copyButton/copyButton.js +++ b/core/src/main/resources/lib/layout/copyButton/copyButton.js @@ -1,4 +1,4 @@ -// @include "org.kohsuke.stapler.zeroclipboard" +// @include org.kohsuke.stapler.zeroclipboard Behaviour.specify("span.copy-button", 'copyButton', 0, function(e) { var btn = e.firstChild; From 6ec5d518cfe4d434279a0bce3f08efc09e2ffaa2 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Wed, 24 Apr 2013 11:11:33 -0700 Subject: [PATCH 018/233] Added missing attributes --- core/src/main/resources/hudson/PluginManager/advanced.jelly | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/core/src/main/resources/hudson/PluginManager/advanced.jelly b/core/src/main/resources/hudson/PluginManager/advanced.jelly index be930610df..32c5316a39 100644 --- a/core/src/main/resources/hudson/PluginManager/advanced.jelly +++ b/core/src/main/resources/hudson/PluginManager/advanced.jelly @@ -36,7 +36,7 @@ THE SOFTWARE.

      ${%HTTP Proxy Configuration}

      - + @@ -46,7 +46,7 @@ THE SOFTWARE. -
      +

      ${%Upload Plugin}

      @@ -67,7 +67,7 @@ THE SOFTWARE.

      ${%Update Site}

      - + From f1669601e4bd607ffa8a809e109f1ad0c79244b1 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Wed, 24 Apr 2013 11:22:44 -0700 Subject: [PATCH 019/233] [FIXED JENKINS-4543] Identify the short name of the plugin from the manifest. --- core/src/main/java/hudson/PluginManager.java | 30 ++++++++++++++++++-- 1 file changed, 27 insertions(+), 3 deletions(-) diff --git a/core/src/main/java/hudson/PluginManager.java b/core/src/main/java/hudson/PluginManager.java index 9c79924e7b..3ef1a3ab06 100644 --- a/core/src/main/java/hudson/PluginManager.java +++ b/core/src/main/java/hudson/PluginManager.java @@ -101,6 +101,7 @@ import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentMap; import java.util.concurrent.CopyOnWriteArrayList; import java.util.concurrent.Future; +import java.util.jar.JarFile; import java.util.logging.Level; import java.util.logging.Logger; import org.xml.sax.Attributes; @@ -729,11 +730,19 @@ public abstract class PluginManager extends AbstractModelObject implements OnMas if(!fileName.endsWith(".jpi") && !fileName.endsWith(".hpi")){ throw new Failure(hudson.model.Messages.Hudson_NotAPlugin(fileName)); } - final String baseName = FilenameUtils.getBaseName(fileName); - new File(rootDir, baseName + ".hpi").delete(); // don't keep confusing legacy *.hpi - fileItem.write(new File(rootDir, baseName + ".jpi")); // rename all new plugins to *.jpi + + // first copy into a temporary file name + File t = File.createTempFile("uploaded", "jp_",rootDir); + fileItem.write(t); // rename all new plugins to *.jpi fileItem.delete(); + final String baseName = identifyPluginShortName(t); + + // and move the temp file into a proper name + new File(rootDir, baseName + ".hpi").delete(); // don't keep confusing legacy *.hpi + new File(rootDir, baseName + ".jpi").delete(); // rename can fail if the file already exists + t.renameTo(new File(rootDir, baseName + ".jpi")); + PluginWrapper existing = getPlugin(baseName); if (existing!=null && existing.isBundled){ existing.doPin(); @@ -749,6 +758,21 @@ public abstract class PluginManager extends AbstractModelObject implements OnMas } } + protected String identifyPluginShortName(File t) { + try { + JarFile j = new JarFile(t); + try { + String name = j.getManifest().getMainAttributes().getValue("Short-Name"); + if (name!=null) return name; + } finally { + j.close(); + } + } catch (IOException e) { + LOGGER.log(WARNING, "Failed to identify the short name from "+t,e); + } + return FilenameUtils.getBaseName(t.getName()); // fall back to the base name of what's uploaded + } + public Descriptor getProxyDescriptor() { return Jenkins.getInstance().getDescriptor(ProxyConfiguration.class); } From 8e6a3f7f03c8cdd93f1fb352088bac9cd2676c49 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Wed, 24 Apr 2013 12:00:58 -0700 Subject: [PATCH 020/233] Converted the build queue and executors into Widgets. --- core/src/main/java/hudson/widgets/Widget.java | 3 +++ .../java/jenkins/widgets/BuildQueueWidget.java | 18 ++++++++++++++++++ .../java/jenkins/widgets/ExecutorsWidget.java | 17 +++++++++++++++++ .../hudson/model/View/sidepanel.jelly | 3 +-- .../jenkins/model/Jenkins/sidepanel.jelly | 2 +- .../widgets/BuildQueueWidget/index.groovy | 7 +++++++ .../widgets/ExecutorsWidget/index.groovy | 5 +++++ 7 files changed, 52 insertions(+), 3 deletions(-) create mode 100644 core/src/main/java/jenkins/widgets/BuildQueueWidget.java create mode 100644 core/src/main/java/jenkins/widgets/ExecutorsWidget.java create mode 100644 core/src/main/resources/jenkins/widgets/BuildQueueWidget/index.groovy create mode 100644 core/src/main/resources/jenkins/widgets/ExecutorsWidget/index.groovy diff --git a/core/src/main/java/hudson/widgets/Widget.java b/core/src/main/java/hudson/widgets/Widget.java index 69153ff3e3..71dad38530 100644 --- a/core/src/main/java/hudson/widgets/Widget.java +++ b/core/src/main/java/hudson/widgets/Widget.java @@ -24,6 +24,7 @@ package hudson.widgets; import hudson.ExtensionPoint; +import hudson.model.View; /** * Box to be rendered in the side panel. @@ -32,6 +33,8 @@ import hudson.ExtensionPoint; *
        *
      • index.jelly should display the widget. It should have: * <l:pane width="2" title="..."> ...body... </l:pane> structure. + * In this view, "it" points to the {@link Widget} and "view" points to {@link View} + * that's rendering the widget. * * @author Kohsuke Kawaguchi * @since 1.146 diff --git a/core/src/main/java/jenkins/widgets/BuildQueueWidget.java b/core/src/main/java/jenkins/widgets/BuildQueueWidget.java new file mode 100644 index 0000000000..93538aada4 --- /dev/null +++ b/core/src/main/java/jenkins/widgets/BuildQueueWidget.java @@ -0,0 +1,18 @@ +package jenkins.widgets; + +import hudson.Extension; +import hudson.widgets.Widget; +import jenkins.model.Jenkins; + +/** + * Show the default build queue. + * + * A plugin may remove this from {@link Jenkins#getWidgets()} and swap in their own. + * + * @author Kohsuke Kawaguchi + * @sine 1.514 + */ +@Extension(ordinal=200) // historically this was the top most widget +public class BuildQueueWidget extends Widget { + +} diff --git a/core/src/main/java/jenkins/widgets/ExecutorsWidget.java b/core/src/main/java/jenkins/widgets/ExecutorsWidget.java new file mode 100644 index 0000000000..4dba7bd61b --- /dev/null +++ b/core/src/main/java/jenkins/widgets/ExecutorsWidget.java @@ -0,0 +1,17 @@ +package jenkins.widgets; + +import hudson.Extension; +import hudson.widgets.Widget; +import jenkins.model.Jenkins; + +/** + * The default executors widget. + * + * A plugin may remove this from {@link Jenkins#getWidgets()} and swap in their own. + * + * @author Kohsuke Kawaguchi + * @since 1.514 + */ +@Extension(ordinal=100) // historically this was above normal widgets and below BuildQueueWidget +public class ExecutorsWidget extends Widget { +} diff --git a/core/src/main/resources/hudson/model/View/sidepanel.jelly b/core/src/main/resources/hudson/model/View/sidepanel.jelly index 599e8a3dc8..0e6336039a 100644 --- a/core/src/main/resources/hudson/model/View/sidepanel.jelly +++ b/core/src/main/resources/hudson/model/View/sidepanel.jelly @@ -70,9 +70,8 @@ THE SOFTWARE. - - + diff --git a/core/src/main/resources/jenkins/model/Jenkins/sidepanel.jelly b/core/src/main/resources/jenkins/model/Jenkins/sidepanel.jelly index 9ddff73647..98697bf4a4 100644 --- a/core/src/main/resources/jenkins/model/Jenkins/sidepanel.jelly +++ b/core/src/main/resources/jenkins/model/Jenkins/sidepanel.jelly @@ -22,5 +22,5 @@ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. --> - +Li \ No newline at end of file diff --git a/core/src/main/resources/jenkins/widgets/BuildQueueWidget/index.groovy b/core/src/main/resources/jenkins/widgets/BuildQueueWidget/index.groovy new file mode 100644 index 0000000000..7001a82644 --- /dev/null +++ b/core/src/main/resources/jenkins/widgets/BuildQueueWidget/index.groovy @@ -0,0 +1,7 @@ +package jenkins.widgets.BuildQueueWidget; + +def t = namespace(lib.JenkinsTagLib.class) + +text(request.ancestors.last().object) + +t.queue(items:view.approximateQueueItemsQuickly) \ No newline at end of file diff --git a/core/src/main/resources/jenkins/widgets/ExecutorsWidget/index.groovy b/core/src/main/resources/jenkins/widgets/ExecutorsWidget/index.groovy new file mode 100644 index 0000000000..f963db4849 --- /dev/null +++ b/core/src/main/resources/jenkins/widgets/ExecutorsWidget/index.groovy @@ -0,0 +1,5 @@ +package jenkins.widgets.ExecutorsWidget + +def t = namespace(lib.JenkinsTagLib.class) + +t.executors(computers:view.computers) \ No newline at end of file From 6117578a435bb6dc886bb09c6b5d86ae2f3bbf30 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Wed, 24 Apr 2013 12:02:07 -0700 Subject: [PATCH 021/233] making notes --- core/src/main/java/hudson/widgets/Widget.java | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/core/src/main/java/hudson/widgets/Widget.java b/core/src/main/java/hudson/widgets/Widget.java index 71dad38530..2aa4863589 100644 --- a/core/src/main/java/hudson/widgets/Widget.java +++ b/core/src/main/java/hudson/widgets/Widget.java @@ -35,6 +35,12 @@ import hudson.model.View; * <l:pane width="2" title="..."> ...body... </l:pane> structure. * In this view, "it" points to the {@link Widget} and "view" points to {@link View} * that's rendering the widget. + *
      + * + * TODO: + * - make Widget describable & provide the UI to let admin configure widgets? + * - backward compatibility implications? + * * * @author Kohsuke Kawaguchi * @since 1.146 From 749775311a07de006935f0438d8d273cd3a92b7f Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Wed, 24 Apr 2013 12:03:44 -0700 Subject: [PATCH 022/233] Oops, that was a debug statement --- .../resources/jenkins/widgets/BuildQueueWidget/index.groovy | 2 -- 1 file changed, 2 deletions(-) diff --git a/core/src/main/resources/jenkins/widgets/BuildQueueWidget/index.groovy b/core/src/main/resources/jenkins/widgets/BuildQueueWidget/index.groovy index 7001a82644..727d053fa9 100644 --- a/core/src/main/resources/jenkins/widgets/BuildQueueWidget/index.groovy +++ b/core/src/main/resources/jenkins/widgets/BuildQueueWidget/index.groovy @@ -2,6 +2,4 @@ package jenkins.widgets.BuildQueueWidget; def t = namespace(lib.JenkinsTagLib.class) -text(request.ancestors.last().object) - t.queue(items:view.approximateQueueItemsQuickly) \ No newline at end of file From 6e91651a574fbc38eae152c8f7dc3c0c7d42fb7b Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Thu, 25 Apr 2013 07:19:02 -0700 Subject: [PATCH 023/233] [JENKINS-16824] log who's interrupting executors. This bug indicates that people are having trouble understanding who's responsible for aborting the build. This change records that information through the logger. --- core/src/main/java/hudson/model/Executor.java | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/core/src/main/java/hudson/model/Executor.java b/core/src/main/java/hudson/model/Executor.java index ee4eddec36..4fcb0968fd 100644 --- a/core/src/main/java/hudson/model/Executor.java +++ b/core/src/main/java/hudson/model/Executor.java @@ -49,6 +49,7 @@ import org.kohsuke.stapler.export.Exported; import javax.servlet.ServletException; import java.io.IOException; import java.util.ArrayList; +import java.util.Arrays; import java.util.List; import java.util.Vector; import java.util.logging.Logger; @@ -135,6 +136,9 @@ public class Executor extends Thread implements ModelObject { * Interrupt the execution. Mark the cause and the status accordingly. */ public void interrupt(Result result, CauseOfInterruption... causes) { + if (LOGGER.isLoggable(FINE)) + LOGGER.log(FINE, String.format("%s is interrupted(%s): %s", getDisplayName(), result, Util.join(Arrays.asList(causes),",")), new InterruptedException()); + interruptStatus = result; synchronized (this.causes) { for (CauseOfInterruption c : causes) { From 405746324411959713835a02ba4a10096372bbdc Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 25 Apr 2013 10:59:11 -0400 Subject: [PATCH 024/233] [JENKINS-16845] Refinement to hotfix: if build field has already been cleared due to earlier warning, do not throw a new NPE. --- core/src/main/java/hudson/tasks/Fingerprinter.java | 3 +++ 1 file changed, 3 insertions(+) diff --git a/core/src/main/java/hudson/tasks/Fingerprinter.java b/core/src/main/java/hudson/tasks/Fingerprinter.java index 2bf37ef36d..b90993a7fc 100644 --- a/core/src/main/java/hudson/tasks/Fingerprinter.java +++ b/core/src/main/java/hudson/tasks/Fingerprinter.java @@ -343,6 +343,9 @@ public class Fingerprinter extends Recorder implements Serializable, DependencyD } public void onLoad() { + if (build == null) { + return; + } if (build.getParent() == null) { logger.warning("JENKINS-16845: broken FingerprintAction record"); build = null; From 7fa8fe4096d0134f598a9d475df1c6199b9b05e7 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 25 Apr 2013 11:20:07 -0400 Subject: [PATCH 025/233] [FIXED JENKINS-17402] getItem may return null but may not throw IAE. --- changelog.html | 3 +++ core/src/main/java/hudson/model/ItemGroup.java | 5 +++-- .../src/main/java/hudson/maven/MavenModuleSet.java | 6 +++++- test/src/test/java/hudson/maven/MavenModuleSetTest.java | 7 +++++++ 4 files changed, 18 insertions(+), 3 deletions(-) diff --git a/changelog.html b/changelog.html index e3949d2bc5..494b3fa505 100644 --- a/changelog.html +++ b/changelog.html @@ -63,6 +63,9 @@ Upcoming changes
    • NPE from MatrixConfiguration.newBuild. (issue 17728) +
    • + NPE configuring Copy Artifact with Maven jobs. + (issue 17402)
    • /about now links to license information for plugins as well.
    • diff --git a/core/src/main/java/hudson/model/ItemGroup.java b/core/src/main/java/hudson/model/ItemGroup.java index 9c7fe37d7c..a87814eb9d 100644 --- a/core/src/main/java/hudson/model/ItemGroup.java +++ b/core/src/main/java/hudson/model/ItemGroup.java @@ -26,6 +26,7 @@ package hudson.model; import java.io.IOException; import java.util.Collection; import java.io.File; +import javax.annotation.CheckForNull; /** * Represents a grouping inherent to a kind of {@link Item}s. @@ -64,9 +65,9 @@ public interface ItemGroup extends PersistenceRoot, ModelObject String getUrlChildPrefix(); /** - * Gets the {@link Item} inside this group that has a given name. + * Gets the {@link Item} inside this group that has a given name, or null if it does not exist. */ - T getItem(String name); + @CheckForNull T getItem(String name); /** * Assigns the {@link Item#getRootDir() root directory} for children. diff --git a/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java b/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java index 31c594da42..d17b8be66a 100644 --- a/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java @@ -434,7 +434,11 @@ public class MavenModuleSet extends AbstractMavenProject Date: Fri, 26 Apr 2013 02:35:20 +0900 Subject: [PATCH 026/233] fixed typo --- core/src/main/resources/jenkins/model/Jenkins/sidepanel.jelly | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/main/resources/jenkins/model/Jenkins/sidepanel.jelly b/core/src/main/resources/jenkins/model/Jenkins/sidepanel.jelly index 98697bf4a4..9ddff73647 100644 --- a/core/src/main/resources/jenkins/model/Jenkins/sidepanel.jelly +++ b/core/src/main/resources/jenkins/model/Jenkins/sidepanel.jelly @@ -22,5 +22,5 @@ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. --> -Li + \ No newline at end of file From 6327e265f89894cd7a8015962655e75fe3de3cae Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Fri, 26 Apr 2013 21:30:37 -0400 Subject: [PATCH 027/233] Added the set-build-parameter command. --- changelog.html | 2 + .../hudson/cli/SetBuildParameterCommand.java | 49 +++++++++++++++++++ .../java/hudson/model/ParametersAction.java | 24 +++++++++ .../resources/hudson/cli/Messages.properties | 1 + .../cli/SetBuildParameterCommandTest.groovy | 47 ++++++++++++++++++ 5 files changed, 123 insertions(+) create mode 100644 core/src/main/java/hudson/cli/SetBuildParameterCommand.java create mode 100644 test/src/test/groovy/hudson/cli/SetBuildParameterCommandTest.groovy diff --git a/changelog.html b/changelog.html index 494b3fa505..2597a65c7d 100644 --- a/changelog.html +++ b/changelog.html @@ -55,6 +55,8 @@ Upcoming changes

      What's new in 1.512 (2013/04/21)

      • From dbf667b5a3cc8f378198b0785f282f2df1485fb9 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sun, 28 Apr 2013 20:36:36 -0700 Subject: [PATCH 030/233] updated changelog as a part of the release --- debian/debian/changelog | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/debian/debian/changelog b/debian/debian/changelog index 5a494da3b2..4f730b9aa7 100644 --- a/debian/debian/changelog +++ b/debian/debian/changelog @@ -1,3 +1,9 @@ +jenkins (1.513) unstable; urgency=low + + * See http://jenkins-ci.org/changelog for more details. + + -- Kohsuke Kawaguchi Sun, 28 Apr 2013 20:23:23 -0700 + jenkins (1.512) unstable; urgency=low * See http://jenkins-ci.org/changelog for more details. From 7df0060b8d174c44231a4f0e32f057679eb88e49 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sun, 28 Apr 2013 21:15:56 -0700 Subject: [PATCH 031/233] creating an RC branch --- changelog.html | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/changelog.html b/changelog.html index f25a7870c1..52c5b53d5a 100644 --- a/changelog.html +++ b/changelog.html @@ -54,6 +54,14 @@ Upcoming changes + + + - - -

        What's new in 1.513 (2013/04/28)

          From 7abd089012e0447cdae0e93cda007bf3daa1cac0 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sun, 28 Apr 2013 21:16:01 -0700 Subject: [PATCH 032/233] the trunk is toward 1.515-SNAPSHOT --- cli/pom.xml | 2 +- core/pom.xml | 2 +- maven-plugin/pom.xml | 2 +- plugins/pom.xml | 12 ++++++------ pom.xml | 2 +- test/pom.xml | 2 +- ui-samples-plugin/pom.xml | 2 +- war/pom.xml | 2 +- 8 files changed, 13 insertions(+), 13 deletions(-) diff --git a/cli/pom.xml b/cli/pom.xml index 1a5ff8a3bd..ac41da3103 100644 --- a/cli/pom.xml +++ b/cli/pom.xml @@ -5,7 +5,7 @@ pom org.jenkins-ci.main - 1.514-SNAPSHOT + 1.515-SNAPSHOT cli diff --git a/core/pom.xml b/core/pom.xml index 636d453829..e2e0f91dff 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.514-SNAPSHOT + 1.515-SNAPSHOT ../pom.xml diff --git a/maven-plugin/pom.xml b/maven-plugin/pom.xml index 3d2bf34dcf..c6d5e29e01 100644 --- a/maven-plugin/pom.xml +++ b/maven-plugin/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.514-SNAPSHOT + 1.515-SNAPSHOT maven-plugin diff --git a/plugins/pom.xml b/plugins/pom.xml index 2cb7948fb8..8d75f27433 100644 --- a/plugins/pom.xml +++ b/plugins/pom.xml @@ -11,7 +11,7 @@ org.jenkins-ci.plugins plugin Jenkins plugin POM - 1.514-SNAPSHOT + 1.515-SNAPSHOT pom org.jenkins-ci.main maven-plugin - 1.514-SNAPSHOT + 1.515-SNAPSHOT @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.514-SNAPSHOT + 1.515-SNAPSHOT test org.jenkins-ci.main jenkins-core - 1.514-SNAPSHOT + 1.515-SNAPSHOT provided org.jenkins-ci.main jenkins-test-harness - 1.514-SNAPSHOT + 1.515-SNAPSHOT test org.jenkins-ci.main ui-samples-plugin - 1.514-SNAPSHOT + 1.515-SNAPSHOT test diff --git a/core/src/main/java/hudson/Functions.java b/core/src/main/java/hudson/Functions.java index c73b72f4c5..cdb19d5bae 100644 --- a/core/src/main/java/hudson/Functions.java +++ b/core/src/main/java/hudson/Functions.java @@ -974,6 +974,67 @@ public class Functions { return Items.getAllItems(root, TopLevelItem.class); } + /** + * Gets the relative name or display name to the given item from the specified group. + * + * @since 1.515 + * @param p the Item we want the relative display name + * @param g the ItemGroup used as point of reference for the item + * @param useDisplayName if true, returns a display name, otherwise returns a name + * @return + * String like "foo Âť bar" + */ + public static String getRelativeNameFrom(Item p, ItemGroup g, boolean useDisplayName) { + if (p == null) return null; + if (g == null) return useDisplayName ? p.getFullDisplayName() : p.getFullName(); + String separationString = useDisplayName ? " Âť " : "/"; + + // first list up all the parents + Map parents = new HashMap(); + int depth=0; + while (g!=null) { + parents.put(g, depth++); + if (g instanceof Item) + g = ((Item)g).getParent(); + else + g = null; + } + + StringBuilder buf = new StringBuilder(); + Item i=p; + while (true) { + if (buf.length()>0) buf.insert(0,separationString); + buf.insert(0,useDisplayName ? i.getDisplayName() : i.getName()); + ItemGroup gr = i.getParent(); + + Integer d = parents.get(gr); + if (d!=null) { + String s=""; + for (int j=d; j>0; j--) + s+=".." + separationString; + return s+buf; + } + + if (gr instanceof Item) + i = (Item)gr; + else + return null; + } + } + + /** + * Gets the name to the given item relative to given group. + * + * @since 1.515 + * @param p the Item we want the relative display name + * @param g the ItemGroup used as point of reference for the item + * @return + * String like "foo Âť bar" + */ + public static String getRelativeNameFrom(Item p, ItemGroup g) { + return getRelativeNameFrom(p, g, false); + } + /** * Gets the relative display name to the given item from the specified group. @@ -985,10 +1046,7 @@ public class Functions { * String like "foo Âť bar" */ public static String getRelativeDisplayNameFrom(Item p, ItemGroup g) { - if (p == null) return null; - String relativeName = p.getRelativeNameFrom(g); - if (relativeName == null) return null; - return relativeName.replace("/", " Âť "); + return getRelativeNameFrom(p, g, true); } public static Map dumpAllThreads() { diff --git a/core/src/main/java/hudson/model/AbstractItem.java b/core/src/main/java/hudson/model/AbstractItem.java index 436e62dfe4..f9acf3759d 100644 --- a/core/src/main/java/hudson/model/AbstractItem.java +++ b/core/src/main/java/hudson/model/AbstractItem.java @@ -327,6 +327,18 @@ public abstract class AbstractItem extends Actionable implements Item, HttpDelet else return n+" \u00BB "+getDisplayName(); } + /** + * Gets the display name of the current item relative to the given group. + * + * @since XXX + * @param p the ItemGroup used as point of reference for the item + * @return + * String like "foo Âť bar" + */ + public String getRelativeDisplayNameFrom(ItemGroup p) { + return Functions.getRelativeDisplayNameFrom(this, p); + } + /** * This method only exists to disambiguate {@link #getRelativeNameFrom(ItemGroup)} and {@link #getRelativeNameFrom(Item)} * @since 1.512 @@ -344,38 +356,7 @@ public abstract class AbstractItem extends Actionable implements Item, HttpDelet * Nested ItemGroups are separated by / character. */ public String getRelativeNameFrom(ItemGroup p) { - if (p == null) return getFullName(); - // first list up all the parents - Map parents = new HashMap(); - int depth=0; - while (p!=null) { - parents.put(p, depth++); - if (p instanceof Item) - p = ((Item)p).getParent(); - else - p = null; - } - - StringBuilder buf = new StringBuilder(); - Item i=this; - while (true) { - if (buf.length()>0) buf.insert(0,'/'); - buf.insert(0,i.getName()); - ItemGroup g = i.getParent(); - - Integer d = parents.get(g); - if (d!=null) { - String s=""; - for (int j=d; j>0; j--) - s+="../"; - return s+buf; - } - - if (g instanceof Item) - i = (Item)g; - else - return null; - } + return Functions.getRelativeNameFrom(this, p); } public String getRelativeNameFrom(Item item) { diff --git a/core/src/test/java/hudson/FunctionsTest.java b/core/src/test/java/hudson/FunctionsTest.java index 03b6179e81..8b703dce22 100644 --- a/core/src/test/java/hudson/FunctionsTest.java +++ b/core/src/test/java/hudson/FunctionsTest.java @@ -28,6 +28,7 @@ import static org.powermock.api.mockito.PowerMockito.mock; import static org.powermock.api.mockito.PowerMockito.mockStatic; import static org.powermock.api.mockito.PowerMockito.when; import hudson.model.Action; +import hudson.model.Item; import hudson.model.ItemGroup; import hudson.model.TopLevelItem; import hudson.model.View; @@ -171,6 +172,30 @@ public class FunctionsTest { assertEquals("job/i/", result); } + @Test + public void testGetRelativeDisplayName() { + Item i = mock(Item.class); + when(i.getName()).thenReturn("jobName"); + when(i.getFullDisplayName()).thenReturn("displayName"); + assertEquals("displayName",Functions.getRelativeDisplayNameFrom(i, null)); + } + + @Test + public void testGetRelativeDisplayNameInsideItemGroup() { + Item i = mock(Item.class); + when(i.getName()).thenReturn("jobName"); + when(i.getDisplayName()).thenReturn("displayName"); + TopLevelItemAndItemGroup ig = mock(TopLevelItemAndItemGroup.class); + Jenkins j = mock(Jenkins.class); + when(ig.getName()).thenReturn("parent"); + when(ig.getDisplayName()).thenReturn("parentDisplay"); + when(ig.getParent()).thenReturn((ItemGroup) j); + when(i.getParent()).thenReturn(ig); + + assertEquals("displayName", Functions.getRelativeDisplayNameFrom(i, ig)); + assertEquals("parentDisplay Âť displayName", Functions.getRelativeDisplayNameFrom(i, j)); + } + private void createMockAncestors(StaplerRequest req, Ancestor... ancestors) { List ancestorsList = Arrays.asList(ancestors); when(req.getAncestors()).thenReturn(ancestorsList); From 3f0f25fc6ba938212ada76feebe640b818842b76 Mon Sep 17 00:00:00 2001 From: ssogabe Date: Tue, 30 Apr 2013 22:09:50 +0900 Subject: [PATCH 036/233] forgot to replace XXX with 1.515 --- core/src/main/java/hudson/model/AbstractItem.java | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/core/src/main/java/hudson/model/AbstractItem.java b/core/src/main/java/hudson/model/AbstractItem.java index f9acf3759d..ecbbbafce5 100644 --- a/core/src/main/java/hudson/model/AbstractItem.java +++ b/core/src/main/java/hudson/model/AbstractItem.java @@ -52,8 +52,6 @@ import org.kohsuke.stapler.export.ExportedBean; import java.io.File; import java.io.IOException; import java.util.Collection; -import java.util.HashMap; -import java.util.Map; import org.kohsuke.stapler.StaplerRequest; import org.kohsuke.stapler.StaplerResponse; @@ -330,7 +328,7 @@ public abstract class AbstractItem extends Actionable implements Item, HttpDelet /** * Gets the display name of the current item relative to the given group. * - * @since XXX + * @since 1.515 * @param p the ItemGroup used as point of reference for the item * @return * String like "foo Âť bar" From f6a8c31f6cdcde1b57f03773dd94e11653d0b6bf Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 30 Apr 2013 09:42:27 -0400 Subject: [PATCH 037/233] TransferResource.getRepositoryUrl is documented to end in a slash if known, so we should not add one. Parsing POMs Downloaded artifact http://repo.jenkins-ci.org/public//org/jenkins-ci/plugins/plugin/1.456/plugin-1.456.pom Downloaded artifact http://repo.jenkins-ci.org/public//org/jenkins-ci/jenkins/1.26/jenkins-1.26.pom --- .../src/main/resources/hudson/maven/Messages.properties | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/maven-plugin/src/main/resources/hudson/maven/Messages.properties b/maven-plugin/src/main/resources/hudson/maven/Messages.properties index c0cb7b938b..b5f430acea 100644 --- a/maven-plugin/src/main/resources/hudson/maven/Messages.properties +++ b/maven-plugin/src/main/resources/hudson/maven/Messages.properties @@ -40,7 +40,7 @@ MavenModuleSet.readResolve_updateConfigProvider=ERROR: Please update the 'config PluginImpl.updateConfiProvider=The current installed version of 'config-file-provider' is not compatible with this core anymore (requires >= 2.3) MavenModuleSetBuild.DiscoveredModule=Discovered a new module {0} {1} -MavenModuleSetBuild.DownloadedArtifact=Downloaded artifact {0}/{1} +MavenModuleSetBuild.DownloadedArtifact=Downloaded artifact {0}{1} MavenModuleSetBuild.FailedToParsePom=Failed to parse POMs MavenModuleSetBuild.FailedToTransfer=Failed to transfer {0} MavenModuleSetBuild.FoundModuleWithoutProject=Found a module with path {0} but no associated project From 0c4fe2ddbac2963c0b633fe27bb1a6016134da50 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 30 Apr 2013 12:07:30 -0400 Subject: [PATCH 038/233] [FIXED JENKINS-17775] Find (model) parent POMs properly during fingerprint recording at end of build. --- changelog.html | 5 +- .../hudson/maven/MavenBuildInformation.java | 13 ++++ .../hudson/maven/MavenModuleSetBuild.java | 41 +++++++++--- .../maven/reporters/MavenFingerprinter.java | 66 +++++-------------- 4 files changed, 67 insertions(+), 58 deletions(-) diff --git a/changelog.html b/changelog.html index 913cc44915..c1f61a48e9 100644 --- a/changelog.html +++ b/changelog.html @@ -58,6 +58,9 @@ Upcoming changes
        • Display Name is not shown. (issue 17715) +
        • + Properly find parent POMs when fingerprinting a Maven project. + (issue 17775)
        @@ -73,7 +76,7 @@ Upcoming changes Third-party license display for core was broken since 1.506. (issue 17724)
      • - Amelioration of exception from fingerprinting in a Maven project when a parent POM could not be located. + Mitigation of exception from fingerprinting in a Maven project when a parent POM could not be located. (issue 17775)
      • NPE from MatrixConfiguration.newBuild. diff --git a/maven-plugin/src/main/java/hudson/maven/MavenBuildInformation.java b/maven-plugin/src/main/java/hudson/maven/MavenBuildInformation.java index cd631dd90f..66dbb24f8c 100644 --- a/maven-plugin/src/main/java/hudson/maven/MavenBuildInformation.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenBuildInformation.java @@ -21,9 +21,13 @@ package hudson.maven; */ import java.io.Serializable; +import java.util.HashMap; +import java.util.Map; import org.apache.commons.lang.StringUtils; import org.apache.maven.artifact.versioning.ComparableVersion; +import org.apache.maven.model.Model; +import org.apache.maven.project.MavenProject; /** * @author Olivier Lamy @@ -33,6 +37,15 @@ public class MavenBuildInformation implements Serializable { private static final long serialVersionUID = -3719709179508200057L; private String mavenVersion; + /** + * Map of model IDs to IDs of the model parents (if defined). + * @see MavenProject#getId + * @see Model#getId + * @see MavenProject#getParent + * @see Model#getParent + * @since 1.515 + */ + public final Map modelParents = new HashMap(); public MavenBuildInformation(String mavenVersion) { this.mavenVersion = mavenVersion; diff --git a/maven-plugin/src/main/java/hudson/maven/MavenModuleSetBuild.java b/maven-plugin/src/main/java/hudson/maven/MavenModuleSetBuild.java index c5874d3d61..2ca820ea64 100644 --- a/maven-plugin/src/main/java/hudson/maven/MavenModuleSetBuild.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenModuleSetBuild.java @@ -65,6 +65,7 @@ import java.io.File; import java.io.IOException; import java.io.InterruptedIOException; import java.io.PrintStream; +import java.io.Serializable; import java.text.MessageFormat; import java.util.ArrayList; import java.util.Collection; @@ -582,7 +583,7 @@ public class MavenModuleSetBuild extends AbstractMavenBuild)MavenModuleSetBuild.this)); @@ -619,7 +620,7 @@ public class MavenModuleSetBuild extends AbstractMavenBuild(); List changedModules = new ArrayList(); @@ -856,12 +857,14 @@ public class MavenModuleSetBuild extends AbstractMavenBuild poms; try { - poms = getModuleRoot().act(new PomParser(listener, mvn, mavenVersion, envVars, MavenModuleSetBuild.this)); + PomParser.Result result = getModuleRoot().act(new PomParser(listener, mvn, mavenVersion, envVars, MavenModuleSetBuild.this)); + poms = result.infos; + mavenBuildInformation.modelParents.putAll(result.modelParents); } catch (IOException e) { if (project.isIncrementalBuild()) { // If POM parsing failed we should do a full build next time. @@ -997,7 +1000,7 @@ public class MavenModuleSetBuild extends AbstractMavenBuild> { + private static final class PomParser implements FileCallable { private final BuildListener listener; private final String rootPOM; /** @@ -1028,7 +1031,7 @@ public class MavenModuleSetBuild extends AbstractMavenBuild invoke(File ws, VirtualChannel channel) throws IOException { + public static final class Result implements Serializable { + public final List infos; + public final Map modelParents; + public Result(List infos, Map modelParents) { + this.infos = infos; + this.modelParents = modelParents; + } + } + + public Result invoke(File ws, VirtualChannel channel) throws IOException { File pom; PrintStream logger = listener.getLogger(); @@ -1194,10 +1206,23 @@ public class MavenModuleSetBuild extends AbstractMavenBuild canonicalPaths = new HashMap( mps.size() ); + Map modelParents = new HashMap(); for(MavenProject mp : mps) { // Projects are indexed by POM path and not module path because // Maven allows to have several POMs with different names in the same directory canonicalPaths.put( mp.getFile().getCanonicalPath(), mp ); + while (true) { + String k = mp.getId(); + if (modelParents.containsKey(k)) { + break; + } + MavenProject mpp = mp.getParent(); + if (mpp == null) { + break; + } + modelParents.put(k, mpp.getId()); + mp = mpp; + } } //MavenUtil.resolveModules(embedder,mp,getRootPath(rootPOMRelPrefix),relPath,listener,nonRecursive); @@ -1225,7 +1250,7 @@ public class MavenModuleSetBuild extends AbstractMavenBuild(infos); + return new Result(new ArrayList(infos), modelParents); } catch (MavenEmbedderException e) { throw new MavenExecutionException(e); } catch (ProjectBuildingException e) { diff --git a/maven-plugin/src/main/java/hudson/maven/reporters/MavenFingerprinter.java b/maven-plugin/src/main/java/hudson/maven/reporters/MavenFingerprinter.java index 1bc8fae8f1..d884a77ea8 100644 --- a/maven-plugin/src/main/java/hudson/maven/reporters/MavenFingerprinter.java +++ b/maven-plugin/src/main/java/hudson/maven/reporters/MavenFingerprinter.java @@ -138,60 +138,28 @@ public class MavenFingerprinter extends MavenReporter { } private void recordParents(MavenBuildProxy build, MavenProject pom, BuildListener listener) throws IOException, InterruptedException { - MavenProject parent = getParent(pom, listener); + Map modelParents = build.getMavenBuildInformation().modelParents; + ArtifactRepository localRepository = getLocalRepository(build.getMavenBuildInformation(), pom); + if (localRepository == null) { + listener.error("Could not find local repository for " + build.getMavenBuildInformation().getMavenVersion()); + return; + } + String parent = modelParents.get(pom.getId()); while (parent != null) { - File parentFile = parent.getFile(); - - if (parentFile == null) { - // Parent artifact contains no actual file, so we resolve against - // the local repository - ArtifactRepository localRepository = getLocalRepository(build.getMavenBuildInformation(), parent, pom); - if (localRepository != null) { - Artifact parentArtifact = getArtifact(parent); - // Don't use ArtifactRepository.find(), for compatibility with Maven 2.x - if (parentArtifact != null) { - parentFile = new File(localRepository.getBasedir(), - localRepository.pathOf(parentArtifact)); - } - } - } - - if (parentFile != null) { - // we need to include the artifact Id for poms as well, otherwise a - // project with the same groupId would override its parent's - // fingerprint - record(parent.getGroupId() + ":" + parent.getArtifactId(), - parentFile, used); - } - parent = getParent(parent, listener); + String[] parts = parent.split(":"); + assert parts.length == 4 : parent; + // Maven 2.x lacks DefaultArtifact constructor with String version and ArtifactRepository.find: + Artifact parentArtifact = new DefaultArtifact(parts[0], parts[1], VersionRange.createFromVersion(parts[3]), null, parts[2], null, new DefaultArtifactHandler(parts[2])); + File parentFile = new File(localRepository.getBasedir(), localRepository.pathOf(parentArtifact)); + // we need to include the artifact Id for poms as well, otherwise a project with the same groupId would override its parent's fingerprint + record(parts[0] + ":" + parts[1], parentFile, used); + parent = modelParents.get(parent); } } - // XXX consider calling also from PomInfo which makes a naked call to getParent - private static MavenProject getParent(MavenProject pom, BuildListener listener) { - try { - return pom.getParent(); - } catch (IllegalStateException x) { // MNG-5075 - x.printStackTrace(listener.error("Warning: failed to resolve parent of " + pom.getId())); - return null; - } - } - - private Artifact getArtifact(MavenProject parent) { - Artifact art = parent.getArtifact(); - if (art == null) { - // happens for Maven 2.x - DefaultArtifactHandler artifactHandler = new DefaultArtifactHandler("pom"); - art = new DefaultArtifact(parent.getGroupId(), parent.getArtifactId(), VersionRange.createFromVersion(parent.getVersion()), - null, "pom", "", artifactHandler); - } - return art; - } - - private ArtifactRepository getLocalRepository(MavenBuildInformation mavenBuildInformation, MavenProject parent, MavenProject pom) { - + private ArtifactRepository getLocalRepository(MavenBuildInformation mavenBuildInformation, MavenProject pom) { if (mavenBuildInformation.isMaven3OrLater()) { - return parent.getProjectBuildingRequest().getLocalRepository(); + return pom.getProjectBuildingRequest().getLocalRepository(); } else if (mavenBuildInformation.isAtLeastMavenVersion("2.2")) { // principally this should also work with Maven 2.1, but it's not tested, so err on the safe side return getArtifactRepositoryMaven21(pom); From b8adcb43dd73f8bcc3ff00558e0f7e587929cec6 Mon Sep 17 00:00:00 2001 From: imod Date: Tue, 30 Apr 2013 20:38:35 +0200 Subject: [PATCH 039/233] add global maven config to define default settings providers --- core/src/main/java/hudson/tasks/Maven.java | 22 +++++++-- .../java/jenkins/mvn/GlobalMavenConfig.java | 47 +++++++++++++++++++ .../mvn/GlobalMavenConfig/config.groovy | 8 ++++ .../java/hudson/maven/MavenModuleSet.java | 14 ++++-- 4 files changed, 81 insertions(+), 10 deletions(-) create mode 100644 core/src/main/java/jenkins/mvn/GlobalMavenConfig.java create mode 100644 core/src/main/resources/jenkins/mvn/GlobalMavenConfig/config.groovy diff --git a/core/src/main/java/hudson/tasks/Maven.java b/core/src/main/java/hudson/tasks/Maven.java index b7c3a2119b..cf77905fa3 100644 --- a/core/src/main/java/hudson/tasks/Maven.java +++ b/core/src/main/java/hudson/tasks/Maven.java @@ -40,6 +40,7 @@ import hudson.model.Node; import jenkins.model.Jenkins; import jenkins.mvn.DefaultGlobalSettingsProvider; import jenkins.mvn.DefaultSettingsProvider; +import jenkins.mvn.GlobalMavenConfig; import jenkins.mvn.GlobalSettingsProvider; import jenkins.mvn.SettingsProvider; import hudson.model.TaskListener; @@ -163,8 +164,8 @@ public class Maven extends Builder { this.properties = Util.fixEmptyAndTrim(properties); this.jvmOptions = Util.fixEmptyAndTrim(jvmOptions); this.usePrivateRepository = usePrivateRepository; - this.settings = settings != null ? settings : new DefaultSettingsProvider(); - this.globalSettings = globalSettings != null ? globalSettings : new DefaultGlobalSettingsProvider(); + this.settings = settings; + this.globalSettings = globalSettings; } public String getTargets() { @@ -175,14 +176,22 @@ public class Maven extends Builder { * @since 1.491 */ public SettingsProvider getSettings() { - return settings != null ? settings : new DefaultSettingsProvider(); + return settings != null ? settings : GlobalMavenConfig.get().getSettingsProvider(); + } + + protected void setSettings(SettingsProvider settings) { + this.settings = settings; } /** * @since 1.491 */ public GlobalSettingsProvider getGlobalSettings() { - return globalSettings != null ? globalSettings : new DefaultGlobalSettingsProvider(); + return globalSettings != null ? globalSettings : GlobalMavenConfig.get().getGlobalSettingsProvider(); + } + + protected void setGlobalSettings(GlobalSettingsProvider globalSettings) { + this.globalSettings = globalSettings; } public void setUsePrivateRepository(boolean usePrivateRepository) { @@ -420,7 +429,10 @@ public class Maven extends Builder { @Override public Builder newInstance(StaplerRequest req, JSONObject formData) throws FormException { - return req.bindJSON(Maven.class,formData); + Maven m = req.bindJSON(Maven.class,formData); + m.setSettings(GlobalMavenConfig.get().getSettingsProvider()); + m.setGlobalSettings(GlobalMavenConfig.get().getGlobalSettingsProvider()); + return m; } } diff --git a/core/src/main/java/jenkins/mvn/GlobalMavenConfig.java b/core/src/main/java/jenkins/mvn/GlobalMavenConfig.java new file mode 100644 index 0000000000..67ace424e8 --- /dev/null +++ b/core/src/main/java/jenkins/mvn/GlobalMavenConfig.java @@ -0,0 +1,47 @@ +package jenkins.mvn; + +import hudson.Extension; +import jenkins.model.GlobalConfiguration; +import net.sf.json.JSONObject; + +import org.kohsuke.stapler.StaplerRequest; + +//as close as it gets to the global Maven Project configuration +@Extension(ordinal = 50) +public class GlobalMavenConfig extends GlobalConfiguration { + private SettingsProvider settingsProvider; + private GlobalSettingsProvider globalSettingsProvider; + + public GlobalMavenConfig() { + load(); + } + + @Override + public boolean configure(StaplerRequest req, JSONObject json) throws FormException { + req.bindJSON(this, json); + return true; + } + + public void setGlobalSettingsProvider(GlobalSettingsProvider globalSettingsProvider) { + this.globalSettingsProvider = globalSettingsProvider; + save(); + } + + public void setSettingsProvider(SettingsProvider settingsProvider) { + this.settingsProvider = settingsProvider; + save(); + } + + public GlobalSettingsProvider getGlobalSettingsProvider() { + return globalSettingsProvider != null ? globalSettingsProvider : new DefaultGlobalSettingsProvider(); + } + + public SettingsProvider getSettingsProvider() { + return settingsProvider != null ? settingsProvider : new DefaultSettingsProvider(); + } + + public static GlobalMavenConfig get() { + return GlobalConfiguration.all().get(GlobalMavenConfig.class); + } + +} diff --git a/core/src/main/resources/jenkins/mvn/GlobalMavenConfig/config.groovy b/core/src/main/resources/jenkins/mvn/GlobalMavenConfig/config.groovy new file mode 100644 index 0000000000..79e427df0f --- /dev/null +++ b/core/src/main/resources/jenkins/mvn/GlobalMavenConfig/config.groovy @@ -0,0 +1,8 @@ +package jenkins.mvn.GlobalMavenConfig; + +def f = namespace(lib.FormTagLib) + +f.section(title:_("Maven Configuration")) { + f.dropdownDescriptorSelector(title:_("Default settings provider"), field:"settingsProvider") + f.dropdownDescriptorSelector(title:_("Default global settings provider"), field:"globalSettingsProvider") +} diff --git a/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java b/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java index d17b8be66a..90b0097265 100644 --- a/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java @@ -94,6 +94,7 @@ import jenkins.model.ModelObjectWithChildren; import jenkins.mvn.DefaultGlobalSettingsProvider; import jenkins.mvn.DefaultSettingsProvider; import jenkins.mvn.FilePathSettingsProvider; +import jenkins.mvn.GlobalMavenConfig; import jenkins.mvn.GlobalSettingsProvider; import jenkins.mvn.GlobalSettingsProviderDescriptor; import jenkins.mvn.SettingsProvider; @@ -284,12 +285,12 @@ public class MavenModuleSet extends AbstractMavenProject Date: Tue, 30 Apr 2013 16:00:00 -0400 Subject: [PATCH 040/233] [FIXED JENKINS-15309] Be robust against serialized ListView with jobNames==null. --- changelog.html | 3 ++ core/src/main/java/hudson/model/ListView.java | 5 +- .../test/java/hudson/model/ListViewTest.java | 44 ++++++++++++++++ .../ListViewTest/nullJobNames/config.xml | 50 +++++++++++++++++++ 4 files changed, 101 insertions(+), 1 deletion(-) create mode 100644 test/src/test/java/hudson/model/ListViewTest.java create mode 100644 test/src/test/resources/hudson/model/ListViewTest/nullJobNames/config.xml diff --git a/changelog.html b/changelog.html index c1f61a48e9..ca690e085b 100644 --- a/changelog.html +++ b/changelog.html @@ -58,6 +58,9 @@ Upcoming changes
      • Display Name is not shown. (issue 17715) +
      • + List views missing a required field were unloadable. + (issue 15309)
      • Properly find parent POMs when fingerprinting a Maven project. (issue 17775) diff --git a/core/src/main/java/hudson/model/ListView.java b/core/src/main/java/hudson/model/ListView.java index 0fd9978c9b..7e1a3eb56f 100644 --- a/core/src/main/java/hudson/model/ListView.java +++ b/core/src/main/java/hudson/model/ListView.java @@ -66,7 +66,7 @@ public class ListView extends View implements Saveable { * List of job names. This is what gets serialized. */ @GuardedBy("this") - /*package*/ final SortedSet jobNames = new TreeSet(CaseInsensitiveComparator.INSTANCE); + /*package*/ /*almost-final*/ SortedSet jobNames = new TreeSet(CaseInsensitiveComparator.INSTANCE); private DescribableList> jobFilters; @@ -108,6 +108,9 @@ public class ListView extends View implements Saveable { private Object readResolve() { if(includeRegex!=null) includePattern = Pattern.compile(includeRegex); + if (jobNames == null) { + jobNames = new TreeSet(CaseInsensitiveComparator.INSTANCE); + } initColumns(); initJobFilters(); return this; diff --git a/test/src/test/java/hudson/model/ListViewTest.java b/test/src/test/java/hudson/model/ListViewTest.java new file mode 100644 index 0000000000..e99ca13ff8 --- /dev/null +++ b/test/src/test/java/hudson/model/ListViewTest.java @@ -0,0 +1,44 @@ +/* + * The MIT License + * + * Copyright 2013 Jesse Glick. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +package hudson.model; + +import static org.junit.Assert.*; +import org.junit.Rule; +import org.junit.Test; +import org.jvnet.hudson.test.Bug; +import org.jvnet.hudson.test.JenkinsRule; +import org.jvnet.hudson.test.recipes.LocalData; + +public class ListViewTest { + + @Rule public JenkinsRule j = new JenkinsRule(); + + @Bug(15309) + @LocalData + @Test public void nullJobNames() throws Exception { + assertTrue(j.jenkins.getView("v").getItems().isEmpty()); + } + +} diff --git a/test/src/test/resources/hudson/model/ListViewTest/nullJobNames/config.xml b/test/src/test/resources/hudson/model/ListViewTest/nullJobNames/config.xml new file mode 100644 index 0000000000..82bd6f3729 --- /dev/null +++ b/test/src/test/resources/hudson/model/ListViewTest/nullJobNames/config.xml @@ -0,0 +1,50 @@ + + + + 1.0 + 2 + NORMAL + true + + + + ${JENKINS_HOME}/workspace/${ITEM_FULLNAME} + ${ITEM_ROOTDIR}/builds + + + + + + 0 + + + + All + false + false + + + + + v + false + false + + + + + + + + + + + + + + All + 0 + + + + \ No newline at end of file From 7f3096c558046edea7bcfefa480193ede429af85 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 30 Apr 2013 16:53:27 -0400 Subject: [PATCH 041/233] Deferring formatting Logger messages unless and until the log formatter is run. No need to call isLoggable if you are only calling simply getters and relying on toString later. --- core/src/main/java/hudson/model/Queue.java | 28 ++++++++++------------ 1 file changed, 12 insertions(+), 16 deletions(-) diff --git a/core/src/main/java/hudson/model/Queue.java b/core/src/main/java/hudson/model/Queue.java index 8de7adb960..ab2bbc7c17 100644 --- a/core/src/main/java/hudson/model/Queue.java +++ b/core/src/main/java/hudson/model/Queue.java @@ -516,7 +516,7 @@ public class Queue extends ResourceController implements Saveable { } } if (duplicatesInQueue.isEmpty()) { - LOGGER.fine(p.getFullDisplayName() + " added to queue"); + LOGGER.log(Level.FINE, "{0} added to queue", p); // put the item in the queue WaitingItem added = new WaitingItem(due,p,actions); @@ -525,7 +525,7 @@ public class Queue extends ResourceController implements Saveable { return added; } - LOGGER.fine(p.getFullDisplayName() + " is already in the queue"); + LOGGER.log(Level.FINE, "{0} is already in the queue", p); // but let the actions affect the existing stuff. for(Item item : duplicatesInQueue) { @@ -593,7 +593,7 @@ public class Queue extends ResourceController implements Saveable { * false if this was no-op. */ public synchronized boolean cancel(Task p) { - LOGGER.fine("Cancelling " + p.getFullDisplayName()); + LOGGER.log(Level.FINE, "Cancelling {0}", p); for (Iterator itr = waitingList.iterator(); itr.hasNext();) { Item item = itr.next(); if (item.task.equals(p)) { @@ -607,7 +607,7 @@ public class Queue extends ResourceController implements Saveable { } public synchronized boolean cancel(Item item) { - LOGGER.fine("Cancelling " + item.task.getFullDisplayName() + " item#" + item.id); + LOGGER.log(Level.FINE, "Cancelling {0} item#{1}", new Object[] {item.task, item.id}); // use bitwise-OR to make sure that all the branches get evaluated all the time boolean r = (item instanceof WaitingItem && waitingList.remove(item)) | blockedProjects.remove(item) | buildables.remove(item); if(r) @@ -890,7 +890,7 @@ public class Queue extends ResourceController implements Saveable { // am I woken up because I have a project to build? if (offer.workUnit != null) { // if so, just build it - LOGGER.fine("Pop returning " + offer.workUnit + " for " + exec.getName()); + LOGGER.log(Level.FINE, "Pop returning {0} for {1}", new Object[] {offer.workUnit, exec.getName()}); // TODO: I think this has to be done by the last executor that leaves the pop(), not by main executor if (offer.workUnit.isMainWork()) @@ -979,8 +979,7 @@ public class Queue extends ResourceController implements Saveable { * and it also gets invoked periodically (see {@link MaintainTask}.) */ public synchronized void maintain() { - if (LOGGER.isLoggable(Level.FINE)) - LOGGER.fine("Queue maintenance started " + this); + LOGGER.log(Level.FINE, "Queue maintenance started {0}", this); {// blocked -> buildable Iterator itr = blockedProjects.values().iterator(); @@ -988,7 +987,7 @@ public class Queue extends ResourceController implements Saveable { BlockedItem p = itr.next(); if (!isBuildBlocked(p) && allowNewBuildableTask(p.task)) { // ready to be executed - LOGGER.fine(p.task.getFullDisplayName() + " no longer blocked"); + LOGGER.log(Level.FINE, "{0} no longer blocked", p.task); itr.remove(); makeBuildable(new BuildableItem(p)); } @@ -1006,12 +1005,12 @@ public class Queue extends ResourceController implements Saveable { Task p = top.task; if (!isBuildBlocked(top) && allowNewBuildableTask(p)) { // ready to be executed immediately - LOGGER.fine(p.getFullDisplayName() + " ready to build"); + LOGGER.log(Level.FINE, "{0} ready to build", p); makeBuildable(new BuildableItem(top)); } else { // this can't be built now because another build is in progress // set this project aside. - LOGGER.fine(p.getFullDisplayName() + " is blocked"); + LOGGER.log(Level.FINE, "{0} is blocked", p); blockedProjects.put(p,new BlockedItem(top)); } } @@ -1029,7 +1028,7 @@ public class Queue extends ResourceController implements Saveable { if (isBuildBlocked(p)) { itr.remove(); blockedProjects.put(p.task,new BlockedItem(p)); - LOGGER.fine(String.format("Catching that %s is blocked in the last minute", p)); + LOGGER.log(Level.FINE, "Catching that {0} is blocked in the last minute", p); continue; } @@ -1044,10 +1043,7 @@ public class Queue extends ResourceController implements Saveable { // if we couldn't find the executor that fits, // just leave it in the buildables list and // check if we can execute other projects - if (LOGGER.isLoggable(Level.FINER)) { - LOGGER.finer(String.format("Failed to map %s to executors. candidates=%s parked=%s", - p, candidates, parked.values())); - } + LOGGER.log(Level.FINER, "Failed to map {0} to executors. candidates={1} parked={2}", new Object[] {p, candidates, parked.values()}); continue; } @@ -1059,7 +1055,7 @@ public class Queue extends ResourceController implements Saveable { if (!wuc.getWorkUnits().isEmpty()) makePending(p); else - LOGGER.fine(String.format("BuildableItem %s with empty work units!?",p)); + LOGGER.log(Level.FINE, "BuildableItem {0} with empty work units!?", p); } } From d391bbee0796b8ad53fb48e5dbf43edf4a36fbfc Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 30 Apr 2013 17:09:28 -0400 Subject: [PATCH 042/233] Debugging toString. --- core/src/main/java/hudson/model/queue/CauseOfBlockage.java | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/core/src/main/java/hudson/model/queue/CauseOfBlockage.java b/core/src/main/java/hudson/model/queue/CauseOfBlockage.java index 44513142a8..4c56340144 100644 --- a/core/src/main/java/hudson/model/queue/CauseOfBlockage.java +++ b/core/src/main/java/hudson/model/queue/CauseOfBlockage.java @@ -43,6 +43,10 @@ public abstract class CauseOfBlockage { }; } + @Override public String toString() { + return getShortDescription(); + } + /** * Marker interface to indicates that we can reasonably expect * that adding a suitable executor/node will resolve this blockage. From 5661af73698a9ec03b256e1d960ae2ede8bad6d0 Mon Sep 17 00:00:00 2001 From: redlab Date: Wed, 1 May 2013 11:06:19 +0200 Subject: [PATCH 043/233] changed the filepath#toUri call to #getRemote as per comment of @jglick --- .../maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java index 8b4b943935..114c783552 100644 --- a/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java +++ b/test/src/test/java/hudson/maven/MavenMultiModuleLogRotatorCleanArtifactsTest.java @@ -82,14 +82,14 @@ public class MavenMultiModuleLogRotatorCleanArtifactsTest { @SuppressWarnings("unchecked") public void testArtifactsAreDeletedInBuildOneWhenBuildDiscarderRun() throws Exception { - File directory = new File(new FilePath(jobs, "test0/builds/1").toURI()); + File directory = new File(new FilePath(jobs, "test0/builds/1").getRemote()); Collection files = FileUtils.listFiles(directory, new String[] { "jar" }, true); Assert.assertTrue( "Found jars in previous build, that should not happen", files.isEmpty()); Collection files2 = FileUtils.listFiles(new File(new FilePath( - jobs, "test0/builds/2").toURI()), new String[] { "jar" }, true); + jobs, "test0/builds/2").getRemote()), new String[] { "jar" }, true); Assert.assertFalse("No jars in last build ALERT!", files2.isEmpty()); } @@ -102,7 +102,7 @@ public class MavenMultiModuleLogRotatorCleanArtifactsTest { public void testArtifactsOldBuildsDeletedWhenBuildDiscarderRun() throws Exception { j.buildAndAssertSuccess(m); - File directory = new File(new FilePath(jobs, "test0/builds/1").toURI()); + File directory = new File(new FilePath(jobs, "test0/builds/1").getRemote()); Assert.assertFalse("oops the build should have been deleted", directory.exists()); } From 2c240bdc876e74fe7a4a1ebeb5e3707e2d8f7bf3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Oliver=20Gond=C5=BEa?= Date: Fri, 1 Mar 2013 08:00:52 +0100 Subject: [PATCH 044/233] [FIXED JENKINS-17030] Enable word breaking for job names --- core/src/main/java/hudson/Functions.java | 16 +++++++++ .../hudson/matrix/MatrixProject/index.jelly | 2 +- .../resources/hudson/model/Job/index.jelly | 2 +- .../hudson/views/JobColumn/column.jelly | 4 +-- .../resources/lib/hudson/buildListTable.jelly | 2 +- .../main/resources/lib/hudson/executors.jelly | 2 +- .../main/resources/lib/hudson/jobLink.jelly | 2 +- .../src/main/resources/lib/hudson/queue.jelly | 2 +- .../main/resources/lib/layout/breakable.jelly | 33 +++++++++++++++++++ core/src/test/java/hudson/FunctionsTest.java | 7 ++++ 10 files changed, 64 insertions(+), 8 deletions(-) create mode 100644 core/src/main/resources/lib/layout/breakable.jelly diff --git a/core/src/main/java/hudson/Functions.java b/core/src/main/java/hudson/Functions.java index cdb19d5bae..be9c3b526e 100644 --- a/core/src/main/java/hudson/Functions.java +++ b/core/src/main/java/hudson/Functions.java @@ -1716,4 +1716,20 @@ public class Functions { DecimalFormat format = new DecimalFormat("#0.00"); return format.format(number) + " " + measure; } + + /** + * Get a string that can be safely broken to several lines when necessary. + * + * This implementation inserts <wbr> tags into string. It allows browsers + * to wrap line before any sequence of punctuation characters or anywhere + * in the middle of prolonged sequences of word characters. + * + * @since 1.516 + */ + public static String breakableString(final String plain) { + + return plain.replaceAll("(\\p{Punct}+\\w)", "$1") + .replaceAll("(\\w{10})(?=\\w{3})", "$1") + ; + } } diff --git a/core/src/main/resources/hudson/matrix/MatrixProject/index.jelly b/core/src/main/resources/hudson/matrix/MatrixProject/index.jelly index 7dbf81516f..de39e50e3a 100644 --- a/core/src/main/resources/hudson/matrix/MatrixProject/index.jelly +++ b/core/src/main/resources/hudson/matrix/MatrixProject/index.jelly @@ -27,7 +27,7 @@ THE SOFTWARE. -

        ${%Project} ${it.displayName}

        +

        ${%Project}

        ${%Project name}: ${it.fullName} diff --git a/core/src/main/resources/hudson/model/Job/index.jelly b/core/src/main/resources/hudson/model/Job/index.jelly index 651b2dd732..9e3c5becd4 100644 --- a/core/src/main/resources/hudson/model/Job/index.jelly +++ b/core/src/main/resources/hudson/model/Job/index.jelly @@ -27,7 +27,7 @@ THE SOFTWARE. -

        ${it.pronoun} ${it.displayName}

        +

        ${it.pronoun}

        ${%Project name}: ${it.fullName} diff --git a/core/src/main/resources/hudson/views/JobColumn/column.jelly b/core/src/main/resources/hudson/views/JobColumn/column.jelly index 116ca8d108..347d4260d2 100644 --- a/core/src/main/resources/hudson/views/JobColumn/column.jelly +++ b/core/src/main/resources/hudson/views/JobColumn/column.jelly @@ -25,6 +25,6 @@ THE SOFTWARE. - ${h.getRelativeDisplayNameFrom(job,currentView.owner.itemGroup)} + - \ No newline at end of file + diff --git a/core/src/main/resources/lib/hudson/buildListTable.jelly b/core/src/main/resources/lib/hudson/buildListTable.jelly index 36d859fa6c..cf2b131db2 100644 --- a/core/src/main/resources/lib/hudson/buildListTable.jelly +++ b/core/src/main/resources/lib/hudson/buildListTable.jelly @@ -53,7 +53,7 @@ THE SOFTWARE. - ${b.parent.fullDisplayName} + ${b.displayName} diff --git a/core/src/main/resources/lib/hudson/executors.jelly b/core/src/main/resources/lib/hudson/executors.jelly index 9ad0e67fab..8bab2b1bd9 100644 --- a/core/src/main/resources/lib/hudson/executors.jelly +++ b/core/src/main/resources/lib/hudson/executors.jelly @@ -79,7 +79,7 @@ THE SOFTWARE. - ${exeparent.fullDisplayName} #${exe.number} +  #${exe.number} diff --git a/core/src/main/resources/lib/hudson/jobLink.jelly b/core/src/main/resources/lib/hudson/jobLink.jelly index dc5d6677dd..fcd234154a 100644 --- a/core/src/main/resources/lib/hudson/jobLink.jelly +++ b/core/src/main/resources/lib/hudson/jobLink.jelly @@ -32,5 +32,5 @@ THE SOFTWARE. ${job.iconColor.description} -${job.fullDisplayName} + diff --git a/core/src/main/resources/lib/hudson/queue.jelly b/core/src/main/resources/lib/hudson/queue.jelly index 7f5488444d..846fccb59a 100644 --- a/core/src/main/resources/lib/hudson/queue.jelly +++ b/core/src/main/resources/lib/hudson/queue.jelly @@ -63,7 +63,7 @@ THE SOFTWARE. - ${item.task.fullDisplayName} + diff --git a/core/src/main/resources/lib/layout/breakable.jelly b/core/src/main/resources/lib/layout/breakable.jelly new file mode 100644 index 0000000000..984b4485d6 --- /dev/null +++ b/core/src/main/resources/lib/layout/breakable.jelly @@ -0,0 +1,33 @@ + + + + + Send escaped value to output decorated to be safely broken into lines when necessary + + Unescaped value to output + + + ${h.breakableString(h.escape(value))} + diff --git a/core/src/test/java/hudson/FunctionsTest.java b/core/src/test/java/hudson/FunctionsTest.java index 8b703dce22..3ef3014d64 100644 --- a/core/src/test/java/hudson/FunctionsTest.java +++ b/core/src/test/java/hudson/FunctionsTest.java @@ -264,4 +264,11 @@ public class FunctionsTest { } } + @Test + public void testBreakableString() { + + assertEquals("Hello world!", Functions.breakableString("Hello world!")); + assertEquals("H,e.l/l:o-w_o=+|d", Functions.breakableString("H,e.l/l:o-w_o=+|d")); + assertEquals("ALongStringThatCanNotBeBrokenByDefault", Functions.breakableString("ALongStringThatCanNotBeBrokenByDefault")); + } } From 9b75fe5c9e9fcb6c1a5862f93be334eb8f5764e5 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Mon, 29 Apr 2013 10:17:04 -0700 Subject: [PATCH 045/233] Hopefully this helps us reduce the screen glitch --- war/src/main/webapp/scripts/hudson-behavior.js | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/war/src/main/webapp/scripts/hudson-behavior.js b/war/src/main/webapp/scripts/hudson-behavior.js index cba3b04d48..18309bdb9c 100644 --- a/war/src/main/webapp/scripts/hudson-behavior.js +++ b/war/src/main/webapp/scripts/hudson-behavior.js @@ -1430,14 +1430,12 @@ function refreshPart(id,url) { var hist = $(id); if (hist==null) console.log("There's no element that has ID of "+id) var p = hist.up(); - var next = hist.next(); - p.removeChild(hist); var div = document.createElement('div'); div.innerHTML = rsp.responseText; var node = $(div).firstDescendant(); - p.insertBefore(node, next); + p.replaceChild(node, hist); Behaviour.applySubtree(node); layoutUpdateCallback.call(); From d482fc50fb59e561b93a0e336680938ffac7fd22 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 24 Apr 2013 16:33:29 -0400 Subject: [PATCH 046/233] [FIXED SECURITY-67] Forbid CSS links in markup to be on the safe side.(cherry picked from commit 1e19eb3ecece1931b5363a797fd2b30f8edc6180) --- core/src/main/java/hudson/markup/MyspacePolicy.java | 1 - core/src/test/java/hudson/markup/MyspacePolicyTest.java | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/core/src/main/java/hudson/markup/MyspacePolicy.java b/core/src/main/java/hudson/markup/MyspacePolicy.java index f0543f9538..46d0c31e22 100644 --- a/core/src/main/java/hudson/markup/MyspacePolicy.java +++ b/core/src/main/java/hudson/markup/MyspacePolicy.java @@ -67,7 +67,6 @@ public class MyspacePolicy { tag("img", "src",ONSITE_OR_OFFSITE_URL, "hspace","vspace"); tag("iframe", "src"); - tag("link", "type","rel"); tag("ul,ol,li,dd,dl,dt,thead,tbody,tfoot"); tag("table", "noresize"); tag("td,th,tr"); diff --git a/core/src/test/java/hudson/markup/MyspacePolicyTest.java b/core/src/test/java/hudson/markup/MyspacePolicyTest.java index cb1a63e2bb..75ac37b28c 100644 --- a/core/src/test/java/hudson/markup/MyspacePolicyTest.java +++ b/core/src/test/java/hudson/markup/MyspacePolicyTest.java @@ -43,7 +43,7 @@ public class MyspacePolicyTest extends Assert { assertReject("script",""); assertIntact(""); - assertIntact(""); + assertReject("link", ""); assertIntact("
        inline CSS
        "); assertIntact("

        "); From 04403edc5863a848ee706e82995aba4675f55968 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 24 Apr 2013 18:02:49 -0400 Subject: [PATCH 047/233] [SECURITY-63] Require POST for running Groovy scripts.(cherry picked from commit 3bbb65df3a5cb2cedb1d8080d6b70697c826a4a9) --- core/src/main/java/hudson/model/Computer.java | 17 +-------- core/src/main/java/jenkins/model/Jenkins.java | 17 ++++++--- .../java/hudson/maven/MavenProbeAction.java | 16 +-------- .../test/java/jenkins/model/JenkinsTest.java | 36 +++++++++++++++++++ 4 files changed, 50 insertions(+), 36 deletions(-) diff --git a/core/src/main/java/hudson/model/Computer.java b/core/src/main/java/hudson/model/Computer.java index cc0edeb367..0778741435 100644 --- a/core/src/main/java/hudson/model/Computer.java +++ b/core/src/main/java/hudson/model/Computer.java @@ -51,8 +51,6 @@ import hudson.slaves.RetentionStrategy; import hudson.slaves.WorkspaceList; import hudson.slaves.OfflineCause; import hudson.slaves.OfflineCause.ByCLI; -import hudson.tasks.BuildWrapper; -import hudson.tasks.Publisher; import hudson.util.DaemonThreadFactory; import hudson.util.EditDistance; import hudson.util.ExceptionCatchingThreadFactory; @@ -1157,20 +1155,7 @@ public /*transient*/ abstract class Computer extends Actionable implements Acces } protected void _doScript( StaplerRequest req, StaplerResponse rsp, String view) throws IOException, ServletException { - // ability to run arbitrary script is dangerous - checkPermission(Jenkins.RUN_SCRIPTS); - - String text = req.getParameter("script"); - if(text!=null) { - try { - req.setAttribute("output", - RemotingDiagnostics.executeGroovy(text,getChannel())); - } catch (InterruptedException e) { - throw new ServletException(e); - } - } - - req.getView(this,view).forward(req, rsp); + Jenkins._doScript(req, rsp, req.getView(this, view), getChannel(), getACL()); } /** diff --git a/core/src/main/java/jenkins/model/Jenkins.java b/core/src/main/java/jenkins/model/Jenkins.java index 7ed3304bac..6fd22fd149 100755 --- a/core/src/main/java/jenkins/model/Jenkins.java +++ b/core/src/main/java/jenkins/model/Jenkins.java @@ -261,6 +261,7 @@ import java.io.InputStream; import java.io.PrintWriter; import java.io.StringWriter; import java.net.BindException; +import java.net.HttpURLConnection; import java.net.URL; import java.nio.charset.Charset; import java.security.SecureRandom; @@ -3357,25 +3358,31 @@ public class Jenkins extends AbstractCIBase implements ModifiableTopLevelItemGro * Run arbitrary Groovy script. */ public void doScript(StaplerRequest req, StaplerResponse rsp) throws IOException, ServletException { - doScript(req, rsp, req.getView(this, "_script.jelly")); + _doScript(req, rsp, req.getView(this, "_script.jelly"), MasterComputer.localChannel, getACL()); } /** * Run arbitrary Groovy script and return result as plain text. */ public void doScriptText(StaplerRequest req, StaplerResponse rsp) throws IOException, ServletException { - doScript(req, rsp, req.getView(this, "_scriptText.jelly")); + _doScript(req, rsp, req.getView(this, "_scriptText.jelly"), MasterComputer.localChannel, getACL()); } - private void doScript(StaplerRequest req, StaplerResponse rsp, RequestDispatcher view) throws IOException, ServletException { + /** + * @since 1.509.1 + */ + public static void _doScript(StaplerRequest req, StaplerResponse rsp, RequestDispatcher view, VirtualChannel channel, ACL acl) throws IOException, ServletException { // ability to run arbitrary script is dangerous - checkPermission(RUN_SCRIPTS); + acl.checkPermission(RUN_SCRIPTS); String text = req.getParameter("script"); if (text != null) { + if (!"POST".equals(req.getMethod())) { + throw HttpResponses.error(HttpURLConnection.HTTP_BAD_METHOD, "requires POST"); + } try { req.setAttribute("output", - RemotingDiagnostics.executeGroovy(text, MasterComputer.localChannel)); + RemotingDiagnostics.executeGroovy(text, channel)); } catch (InterruptedException e) { throw new ServletException(e); } diff --git a/maven-plugin/src/main/java/hudson/maven/MavenProbeAction.java b/maven-plugin/src/main/java/hudson/maven/MavenProbeAction.java index dbf4acf2bb..5efe9ee56c 100644 --- a/maven-plugin/src/main/java/hudson/maven/MavenProbeAction.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenProbeAction.java @@ -97,21 +97,7 @@ public final class MavenProbeAction implements Action { } public void doScript( StaplerRequest req, StaplerResponse rsp ) throws IOException, ServletException { - // ability to run arbitrary script is dangerous, - // so tie it to the admin access - owner.checkPermission(Jenkins.RUN_SCRIPTS); - - String text = req.getParameter("script"); - if(text!=null) { - try { - req.setAttribute("output", - RemotingDiagnostics.executeGroovy(text,channel)); - } catch (InterruptedException e) { - throw new ServletException(e); - } - } - - req.getView(this,"_script.jelly").forward(req,rsp); + Jenkins._doScript(req, rsp, req.getView(this, "_script.jelly"), channel, owner.getACL()); } /** diff --git a/test/src/test/java/jenkins/model/JenkinsTest.java b/test/src/test/java/jenkins/model/JenkinsTest.java index 46700d5195..6859e83b58 100644 --- a/test/src/test/java/jenkins/model/JenkinsTest.java +++ b/test/src/test/java/jenkins/model/JenkinsTest.java @@ -23,6 +23,8 @@ */ package jenkins.model; +import com.gargoylesoftware.htmlunit.HttpMethod; +import com.gargoylesoftware.htmlunit.WebRequestSettings; import com.gargoylesoftware.htmlunit.html.HtmlForm; import hudson.maven.MavenModuleSet; import hudson.maven.MavenModuleSetBuild; @@ -32,6 +34,9 @@ import hudson.security.FullControlOnceLoggedInAuthorizationStrategy; import hudson.util.HttpResponses; import junit.framework.Assert; import hudson.model.FreeStyleProject; +import hudson.security.GlobalMatrixAuthorizationStrategy; +import hudson.security.LegacySecurityRealm; +import hudson.security.Permission; import hudson.util.FormValidation; import org.junit.Test; @@ -41,6 +46,7 @@ import org.jvnet.hudson.test.HudsonTestCase; import org.jvnet.hudson.test.TestExtension; import org.kohsuke.stapler.HttpResponse; import java.net.HttpURLConnection; +import java.net.URL; /** * @author kingfai @@ -237,6 +243,36 @@ public class JenkinsTest extends HudsonTestCase { assertEquals(3,jenkins.getExtensionList(RootAction.class).get(RootActionImpl.class).count); } + public void testDoScript() throws Exception { + jenkins.setSecurityRealm(new LegacySecurityRealm()); + GlobalMatrixAuthorizationStrategy gmas = new GlobalMatrixAuthorizationStrategy() { + @Override public boolean hasPermission(String sid, Permission p) { + return p == Jenkins.RUN_SCRIPTS ? hasExplicitPermission(sid, p) : super.hasPermission(sid, p); + } + }; + gmas.add(Jenkins.ADMINISTER, "alice"); + gmas.add(Jenkins.RUN_SCRIPTS, "alice"); + gmas.add(Jenkins.READ, "bob"); + gmas.add(Jenkins.ADMINISTER, "charlie"); + jenkins.setAuthorizationStrategy(gmas); + WebClient wc = createWebClient(); + wc.login("alice"); + wc.goTo("script"); + wc.assertFails("script?script=System.setProperty('hack','me')", HttpURLConnection.HTTP_BAD_METHOD); + assertNull(System.getProperty("hack")); + WebRequestSettings req = new WebRequestSettings(new URL(wc.getContextPath() + "script?script=System.setProperty('hack','me')"), HttpMethod.POST); + wc.getPage(wc.addCrumb(req)); + assertEquals("me", System.getProperty("hack")); + wc.assertFails("scriptText?script=System.setProperty('hack','me')", HttpURLConnection.HTTP_BAD_METHOD); + req = new WebRequestSettings(new URL(wc.getContextPath() + "scriptText?script=System.setProperty('huck','you')"), HttpMethod.POST); + wc.getPage(wc.addCrumb(req)); + assertEquals("you", System.getProperty("huck")); + wc.login("bob"); + wc.assertFails("script", HttpURLConnection.HTTP_FORBIDDEN); + wc.login("charlie"); + wc.assertFails("script", HttpURLConnection.HTTP_FORBIDDEN); + } + @TestExtension("testUnprotectedRootAction") public static class RootActionImpl implements UnprotectedRootAction { private int count; From 1e51b62298d37753f6b2d2f70eb179ab950d1456 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 24 Apr 2013 18:32:01 -0400 Subject: [PATCH 048/233] [SECURITY-63] Check RUN_SCRIPTS for /eval.(cherry picked from commit 3d03990abc68f39e7a92ed9594abb658879a6d7b) --- core/src/main/java/jenkins/model/Jenkins.java | 2 +- .../test/java/jenkins/model/JenkinsTest.java | 40 +++++++++++++++++++ 2 files changed, 41 insertions(+), 1 deletion(-) diff --git a/core/src/main/java/jenkins/model/Jenkins.java b/core/src/main/java/jenkins/model/Jenkins.java index 6fd22fd149..b2efe0caa5 100755 --- a/core/src/main/java/jenkins/model/Jenkins.java +++ b/core/src/main/java/jenkins/model/Jenkins.java @@ -3398,7 +3398,7 @@ public class Jenkins extends AbstractCIBase implements ModifiableTopLevelItemGro */ @RequirePOST public void doEval(StaplerRequest req, StaplerResponse rsp) throws IOException, ServletException { - checkPermission(ADMINISTER); + checkPermission(RUN_SCRIPTS); try { MetaClass mc = WebApp.getCurrent().getMetaClass(getClass()); diff --git a/test/src/test/java/jenkins/model/JenkinsTest.java b/test/src/test/java/jenkins/model/JenkinsTest.java index 6859e83b58..250d9591f5 100644 --- a/test/src/test/java/jenkins/model/JenkinsTest.java +++ b/test/src/test/java/jenkins/model/JenkinsTest.java @@ -23,6 +23,7 @@ */ package jenkins.model; +import com.gargoylesoftware.htmlunit.FailingHttpStatusCodeException; import com.gargoylesoftware.htmlunit.HttpMethod; import com.gargoylesoftware.htmlunit.WebRequestSettings; import com.gargoylesoftware.htmlunit.html.HtmlForm; @@ -273,6 +274,45 @@ public class JenkinsTest extends HudsonTestCase { wc.assertFails("script", HttpURLConnection.HTTP_FORBIDDEN); } + public void testDoEval() throws Exception { + jenkins.setSecurityRealm(new LegacySecurityRealm()); + GlobalMatrixAuthorizationStrategy gmas = new GlobalMatrixAuthorizationStrategy() { + @Override public boolean hasPermission(String sid, Permission p) { + return p == Jenkins.RUN_SCRIPTS ? hasExplicitPermission(sid, p) : super.hasPermission(sid, p); + } + }; + gmas.add(Jenkins.ADMINISTER, "alice"); + gmas.add(Jenkins.RUN_SCRIPTS, "alice"); + gmas.add(Jenkins.READ, "bob"); + gmas.add(Jenkins.ADMINISTER, "charlie"); + jenkins.setAuthorizationStrategy(gmas); + // Otherwise get "RuntimeException: Trying to set the request parameters, but the request body has already been specified;the two are mutually exclusive!" from WebRequestSettings.setRequestParameters when POSTing content: + jenkins.setCrumbIssuer(null); + WebClient wc = createWebClient(); + wc.login("alice"); + wc.assertFails("eval", HttpURLConnection.HTTP_INTERNAL_ERROR); + assertEquals("3", eval(wc)); + wc.login("bob"); + try { + eval(wc); + fail("bob has only READ"); + } catch (FailingHttpStatusCodeException e) { + assertEquals(HttpURLConnection.HTTP_FORBIDDEN, e.getStatusCode()); + } + wc.login("charlie"); + try { + eval(wc); + fail("charlie has ADMINISTER but not RUN_SCRIPTS"); + } catch (FailingHttpStatusCodeException e) { + assertEquals(HttpURLConnection.HTTP_FORBIDDEN, e.getStatusCode()); + } + } + private String eval(WebClient wc) throws Exception { + WebRequestSettings req = new WebRequestSettings(new URL(wc.getContextPath() + "eval"), HttpMethod.POST); + req.setRequestBody("${1+2}"); + return wc.getPage(/*wc.addCrumb(*/req/*)*/).getWebResponse().getContentAsString(); + } + @TestExtension("testUnprotectedRootAction") public static class RootActionImpl implements UnprotectedRootAction { private int count; From 8063a27abbe3fbe28b11ef6f6a6af70f43f32e91 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 24 Apr 2013 18:50:47 -0400 Subject: [PATCH 049/233] [FIXED SECURITY-69] Require POST to redeploy artifacts.(cherry picked from commit 3e56c3fc1884c8cdbfe9da55c689d26461592f55) --- .../hudson/maven/reporters/MavenAbstractArtifactRecord.java | 2 ++ 1 file changed, 2 insertions(+) diff --git a/maven-plugin/src/main/java/hudson/maven/reporters/MavenAbstractArtifactRecord.java b/maven-plugin/src/main/java/hudson/maven/reporters/MavenAbstractArtifactRecord.java index 482fc70c48..95681e5eb6 100644 --- a/maven-plugin/src/main/java/hudson/maven/reporters/MavenAbstractArtifactRecord.java +++ b/maven-plugin/src/main/java/hudson/maven/reporters/MavenAbstractArtifactRecord.java @@ -65,6 +65,7 @@ import org.kohsuke.stapler.StaplerRequest; import org.kohsuke.stapler.StaplerResponse; import org.kohsuke.stapler.export.Exported; import org.kohsuke.stapler.export.ExportedBean; +import org.kohsuke.stapler.interceptor.RequirePOST; /** * UI to redeploy artifacts after the fact. @@ -208,6 +209,7 @@ public abstract class MavenAbstractArtifactRecord> /** * Performs a redeployment. */ + @RequirePOST public final HttpResponse doRedeploy( @QueryParameter("_.id") final String id, @QueryParameter("_.url") final String repositoryUrl, From f7e266efb611a323229028ecaa238dde43570cd5 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Wed, 24 Apr 2013 18:04:03 -0700 Subject: [PATCH 050/233] [FIXED SECURITY-71] (cherry picked from commit 4f0200a06d1a57a908a37428cfb25ebc7f61fe69) --- core/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/pom.xml b/core/pom.xml index 636d453829..b5bf91e598 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -164,7 +164,7 @@ THE SOFTWARE. org.kohsuke.stapler stapler-adjunct-zeroclipboard - 1.0.7-2 + 1.1.7-1 org.kohsuke.stapler From 499fcaa1892fd9b486a6980c60e91a8286b57c9b Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Wed, 1 May 2013 14:23:06 -0700 Subject: [PATCH 051/233] recording fixes --- changelog.html | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/changelog.html b/changelog.html index 52c5b53d5a..bae88f79b2 100644 --- a/changelog.html +++ b/changelog.html @@ -94,6 +94,15 @@ Upcoming changes
      • Breadcrumb is reworked to show descendants to provide additional navigational shortcuts. (discussion) +
      • + Fixed CSRF vulnerabilities + (SECURITY-63,SECURITY-69) +
      • + Fixed an XSS vulnerability via stylesheet + (SECURITY-67) +
      • + Fixed an XSS vulnerability to copy arbitrary text into clipboard + (SECURITY-71/CVE-2013-1808)

      What's new in 1.512 (2013/04/21)

        From 00d5e38759d08fa89ef366fd430e900f4138f0af Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 1 May 2013 19:10:30 -0400 Subject: [PATCH 052/233] [JENKINS-17681] Set up a test which passes on Unix but fails on Windows when symlinks are enabled on the platform but disabled for the current user. --- .../java/jenkins/model/PeepholePermalink.java | 43 +++++++++++------- .../jenkins/model/PeepholePermalinkTest.java | 45 +++++++++++++++++++ 2 files changed, 71 insertions(+), 17 deletions(-) create mode 100644 core/src/test/java/jenkins/model/PeepholePermalinkTest.java diff --git a/core/src/main/java/jenkins/model/PeepholePermalink.java b/core/src/main/java/jenkins/model/PeepholePermalink.java index aedd8325b5..2e4677a134 100644 --- a/core/src/main/java/jenkins/model/PeepholePermalink.java +++ b/core/src/main/java/jenkins/model/PeepholePermalink.java @@ -81,12 +81,7 @@ public abstract class PeepholePermalink extends Permalink implements Predicate b=null; try { - String target = Util.resolveSymlink(f); - if (target==null && f.exists()) { - // if this file isn't a symlink, it must be a regular file - target = FileUtils.readFileToString(f,"UTF-8").trim(); - } - + String target = readSymlink(f); if (target!=null) { int n = Integer.parseInt(Util.getFileName(target)); if (n==RESOLVES_TO_NONE) return null; @@ -135,19 +130,39 @@ public abstract class PeepholePermalink extends Permalink implements Predicate Date: Wed, 1 May 2013 20:12:59 -0400 Subject: [PATCH 053/233] [FIXED JENKINS-17681] Do not try to call resolveSymlink on a nonexistent link as you will just get an IOException, breaking peephole permalinks in some Windows environments. --- changelog.html | 3 +++ core/src/main/java/hudson/Util.java | 4 ++++ .../src/main/java/jenkins/model/PeepholePermalink.java | 10 +++++++++- 3 files changed, 16 insertions(+), 1 deletion(-) diff --git a/changelog.html b/changelog.html index ca690e085b..8e738d6328 100644 --- a/changelog.html +++ b/changelog.html @@ -58,6 +58,9 @@ Upcoming changes
      • Display Name is not shown. (issue 17715) +
      • + Symlink handling problem with build permalinks on Windows. + (issue 17681)
      • List views missing a required field were unloadable. (issue 15309) diff --git a/core/src/main/java/hudson/Util.java b/core/src/main/java/hudson/Util.java index 1365bca2be..511d9eefa8 100644 --- a/core/src/main/java/hudson/Util.java +++ b/core/src/main/java/hudson/Util.java @@ -1200,6 +1200,10 @@ public class Util { } catch (ClassNotFoundException x3) { assert false : x3; // should be Java 7+ here } + if (x2.getClass().getName().equals("java.nio.file.FileSystemException")) { + // Thrown ("Incorrect function.") on JDK 7u21 in Windows 2012 when called on a non-symlink, rather than NotLinkException, contrary to documentation. Maybe only when not on NTFS? + return null; + } if (x2 instanceof IOException) { throw (IOException) x2; } diff --git a/core/src/main/java/jenkins/model/PeepholePermalink.java b/core/src/main/java/jenkins/model/PeepholePermalink.java index 2e4677a134..397d035743 100644 --- a/core/src/main/java/jenkins/model/PeepholePermalink.java +++ b/core/src/main/java/jenkins/model/PeepholePermalink.java @@ -17,6 +17,7 @@ import javax.annotation.Nullable; import java.io.File; import java.io.IOException; import java.io.StringWriter; +import java.util.Arrays; import java.util.logging.Level; import java.util.logging.Logger; @@ -143,6 +144,12 @@ public abstract class PeepholePermalink extends Permalink implements Predicate Date: Wed, 1 May 2013 19:48:55 -0700 Subject: [PATCH 054/233] [maven-release-plugin] prepare release jenkins-1.514 --- cli/pom.xml | 2 +- core/pom.xml | 2 +- maven-plugin/pom.xml | 2 +- plugins/pom.xml | 12 ++++++------ pom.xml | 2 +- test/pom.xml | 2 +- ui-samples-plugin/pom.xml | 2 +- war/pom.xml | 2 +- 8 files changed, 13 insertions(+), 13 deletions(-) diff --git a/cli/pom.xml b/cli/pom.xml index 1a5ff8a3bd..d7070f9fb7 100644 --- a/cli/pom.xml +++ b/cli/pom.xml @@ -5,7 +5,7 @@ pom org.jenkins-ci.main - 1.514-SNAPSHOT + 1.514 cli diff --git a/core/pom.xml b/core/pom.xml index b5bf91e598..5dd4fa8863 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.514-SNAPSHOT + 1.514 ../pom.xml diff --git a/maven-plugin/pom.xml b/maven-plugin/pom.xml index 3d2bf34dcf..98974b9a5f 100644 --- a/maven-plugin/pom.xml +++ b/maven-plugin/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.514-SNAPSHOT + 1.514 maven-plugin diff --git a/plugins/pom.xml b/plugins/pom.xml index 2cb7948fb8..8e55ba274c 100644 --- a/plugins/pom.xml +++ b/plugins/pom.xml @@ -11,7 +11,7 @@ org.jenkins-ci.plugins plugin Jenkins plugin POM - 1.514-SNAPSHOT + 1.514 pom org.jenkins-ci.main maven-plugin - 1.514-SNAPSHOT + 1.514 @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.514-SNAPSHOT + 1.514 test org.jenkins-ci.main jenkins-core - 1.514-SNAPSHOT + 1.514 provided org.jenkins-ci.main jenkins-test-harness - 1.514-SNAPSHOT + 1.514 test org.jenkins-ci.main ui-samples-plugin - 1.514-SNAPSHOT + 1.514 test org.jenkins-ci.main maven-plugin - 1.514 + 1.515-SNAPSHOT @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.514 + 1.515-SNAPSHOT test org.jenkins-ci.main jenkins-core - 1.514 + 1.515-SNAPSHOT provided org.jenkins-ci.main jenkins-test-harness - 1.514 + 1.515-SNAPSHOT test org.jenkins-ci.main ui-samples-plugin - 1.514 + 1.515-SNAPSHOT test +

        What's new in 1.514 (2013/05/01)

        • Added a new set-build-parameter command that can update a build variable from within a build. @@ -81,7 +84,6 @@ Upcoming changes
        • Updated bundled plugins.
        -

        What's new in 1.513 (2013/04/28)

        • From 384544c7cfde1c4d16de92caf1ea6aa2d59b6507 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Wed, 1 May 2013 20:37:27 -0700 Subject: [PATCH 057/233] updated changelog as a part of the release --- debian/debian/changelog | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/debian/debian/changelog b/debian/debian/changelog index 4f730b9aa7..9db182f2e9 100644 --- a/debian/debian/changelog +++ b/debian/debian/changelog @@ -1,3 +1,9 @@ +jenkins (1.514) unstable; urgency=low + + * See http://jenkins-ci.org/changelog for more details. + + -- Kohsuke Kawaguchi Wed, 01 May 2013 20:15:32 -0700 + jenkins (1.513) unstable; urgency=low * See http://jenkins-ci.org/changelog for more details. From 09ae9c00d39dbe824e5f0fdcd8861ec245ed057f Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 2 May 2013 08:51:09 -0400 Subject: [PATCH 058/233] [JENKINS-17508] Noting. --- changelog.html | 3 +++ 1 file changed, 3 insertions(+) diff --git a/changelog.html b/changelog.html index 178863ca3f..b02562a180 100644 --- a/changelog.html +++ b/changelog.html @@ -64,6 +64,9 @@ Upcoming changes
        • List views missing a required field were unloadable. (issue 15309) +
        • + Maven module artifacts were not being deleted by the log rotator. + (issue 17508)
        • Properly find parent POMs when fingerprinting a Maven project. (issue 17775) From 21bf5c45d4249dd4cbb52c0cc61ef3ae117d3dc6 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 2 May 2013 08:55:31 -0400 Subject: [PATCH 059/233] Diagnosis for test failure. https://jenkins.ci.cloudbees.com/job/core/job/jenkins_main_trunk/850/testReport/jenkins.security/RekeySecretAdminMonitorTest/testBasicWorkflow/ com.gargoylesoftware.htmlunit.FailingHttpStatusCodeException: 400 Bad Request for http://localhost:60027//administrativeMonitor/jenkins.security.RekeySecretAdminMonitor/scan at com.gargoylesoftware.htmlunit.WebClient.throwFailingHttpStatusCodeExceptionIfNecessary(WebClient.java:549) at com.gargoylesoftware.htmlunit.WebClient.getPage(WebClient.java:333) at com.gargoylesoftware.htmlunit.WebClient.getPage(WebClient.java:357) at com.gargoylesoftware.htmlunit.html.HtmlForm.submit(HtmlForm.java:196) at org.jvnet.hudson.test.HudsonTestCase.submit(HudsonTestCase.java:1178) at jenkins.security.RekeySecretAdminMonitorTest.testBasicWorkflow(RekeySecretAdminMonitorTest.java:112) java.lang.Exception: Invalid request submission at org.kohsuke.stapler.HttpResponses.error(HttpResponses.java:79) at jenkins.security.RekeySecretAdminMonitor.doScan(RekeySecretAdminMonitor.java:117) --- .../src/main/java/jenkins/security/RekeySecretAdminMonitor.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/main/java/jenkins/security/RekeySecretAdminMonitor.java b/core/src/main/java/jenkins/security/RekeySecretAdminMonitor.java index a5ce72c824..6ccfabd1e3 100644 --- a/core/src/main/java/jenkins/security/RekeySecretAdminMonitor.java +++ b/core/src/main/java/jenkins/security/RekeySecretAdminMonitor.java @@ -114,7 +114,7 @@ public class RekeySecretAdminMonitor extends AdministrativeMonitor implements St if(req.hasParameter("dismiss")) { disable(true); } else - throw HttpResponses.error(400,"Invalid request submission"); + throw HttpResponses.error(400,"Invalid request submission: " + req.getParameterMap()); return HttpResponses.redirectViaContextPath("/manage"); } From d658f55c3076e4aadc8f428f76399661ff77e0bf Mon Sep 17 00:00:00 2001 From: Donny Nadolny Date: Thu, 2 May 2013 13:49:03 -0400 Subject: [PATCH 060/233] Add extension point to rewrite JUnit test names This adds an extension point, TestNameTransformer, which is called to transform JUnit test case names. This is useful for JVM languages like scala which are more flexible than java with identifier naming. Scala, for example, allows you to write test names between back ticks, and then encodes the name using valid java identifiers. This extension point would allow a plugin to transform those names back in to readable names when they are displayed on the test result page. --- .../java/hudson/tasks/junit/CaseResult.java | 13 +++--- .../java/hudson/tasks/junit/ClassResult.java | 10 +++-- .../hudson/tasks/junit/PackageResult.java | 4 +- .../tasks/junit/TestNameTransformer.java | 42 +++++++++++++++++++ .../hudson/tasks/junit/CaseResult/index.jelly | 2 +- .../hudson/tasks/junit/ClassResult/body.jelly | 2 +- .../AbstractTestResultAction/summary.jelly | 2 +- .../tasks/test/MetaTabulatedResult/body.jelly | 4 +- .../hudson/tasks/junit/SuiteResultTest.java | 4 +- .../tasks/junit/TestNameTransformerTest.java | 27 ++++++++++++ .../tasks/junit/TestResultPublishingTest.java | 2 +- 11 files changed, 94 insertions(+), 18 deletions(-) create mode 100644 core/src/main/java/hudson/tasks/junit/TestNameTransformer.java create mode 100644 test/src/test/java/hudson/tasks/junit/TestNameTransformerTest.java diff --git a/core/src/main/java/hudson/tasks/junit/CaseResult.java b/core/src/main/java/hudson/tasks/junit/CaseResult.java index 899fc36ce1..6111f2690f 100644 --- a/core/src/main/java/hudson/tasks/junit/CaseResult.java +++ b/core/src/main/java/hudson/tasks/junit/CaseResult.java @@ -214,7 +214,7 @@ public final class CaseResult extends TestResult implements Comparable all() { + return Jenkins.getInstance().getExtensionList(TestNameTransformer.class); + } +} diff --git a/core/src/main/resources/hudson/tasks/junit/CaseResult/index.jelly b/core/src/main/resources/hudson/tasks/junit/CaseResult/index.jelly index 036d0211a2..b68fefc07c 100644 --- a/core/src/main/resources/hudson/tasks/junit/CaseResult/index.jelly +++ b/core/src/main/resources/hudson/tasks/junit/CaseResult/index.jelly @@ -34,7 +34,7 @@ THE SOFTWARE.

          - + (from ) diff --git a/core/src/main/resources/hudson/tasks/junit/ClassResult/body.jelly b/core/src/main/resources/hudson/tasks/junit/ClassResult/body.jelly index 2c6b7b5dd1..6e5f67cfc9 100644 --- a/core/src/main/resources/hudson/tasks/junit/ClassResult/body.jelly +++ b/core/src/main/resources/hudson/tasks/junit/ClassResult/body.jelly @@ -36,7 +36,7 @@ THE SOFTWARE. - + diff --git a/core/src/main/resources/hudson/tasks/test/AbstractTestResultAction/summary.jelly b/core/src/main/resources/hudson/tasks/test/AbstractTestResultAction/summary.jelly index 02301cffbc..38bc5c55af 100644 --- a/core/src/main/resources/hudson/tasks/test/AbstractTestResultAction/summary.jelly +++ b/core/src/main/resources/hudson/tasks/test/AbstractTestResultAction/summary.jelly @@ -66,7 +66,7 @@ THE SOFTWARE. - +

        • diff --git a/core/src/main/resources/hudson/tasks/test/MetaTabulatedResult/body.jelly b/core/src/main/resources/hudson/tasks/test/MetaTabulatedResult/body.jelly index ab82ece584..22fcb47390 100644 --- a/core/src/main/resources/hudson/tasks/test/MetaTabulatedResult/body.jelly +++ b/core/src/main/resources/hudson/tasks/test/MetaTabulatedResult/body.jelly @@ -63,7 +63,7 @@ THE SOFTWARE. - + @@ -102,7 +102,7 @@ THE SOFTWARE. - + diff --git a/core/src/test/java/hudson/tasks/junit/SuiteResultTest.java b/core/src/test/java/hudson/tasks/junit/SuiteResultTest.java index ffeb8a0c8d..5e9d486459 100644 --- a/core/src/test/java/hudson/tasks/junit/SuiteResultTest.java +++ b/core/src/test/java/hudson/tasks/junit/SuiteResultTest.java @@ -82,7 +82,7 @@ public class SuiteResultTest extends TestCase { List cases = result.getCases(); for (CaseResult caseResult : cases) { - assertEquals("Test class name is incorrect in " + caseResult.getDisplayName(), "WLI-FI-Tests-Fake", caseResult.getClassName()); + assertEquals("Test class name is incorrect in " + caseResult.getName(), "WLI-FI-Tests-Fake", caseResult.getClassName()); } assertEquals("Test name is incorrect", "IF_importTradeConfirmationToDwh", cases.get(0).getName()); assertEquals("Test name is incorrect", "IF_getAmartaDisbursements", cases.get(1).getName()); @@ -119,7 +119,7 @@ public class SuiteResultTest extends TestCase { List cases = result.getCases(); for (CaseResult caseResult : cases) { - assertEquals("Test class name is incorrect in " + caseResult.getDisplayName(), "some.package.somewhere.WhooHoo", caseResult.getClassName()); + assertEquals("Test class name is incorrect in " + caseResult.getName(), "some.package.somewhere.WhooHoo", caseResult.getClassName()); } assertEquals("this normally has the string like, expected mullet, but got bream", cases.get(0).getErrorDetails()); } diff --git a/test/src/test/java/hudson/tasks/junit/TestNameTransformerTest.java b/test/src/test/java/hudson/tasks/junit/TestNameTransformerTest.java new file mode 100644 index 0000000000..68e32150b3 --- /dev/null +++ b/test/src/test/java/hudson/tasks/junit/TestNameTransformerTest.java @@ -0,0 +1,27 @@ +package hudson.tasks.junit; + +import hudson.Extension; + +import org.jvnet.hudson.test.HudsonTestCase; + +public class TestNameTransformerTest extends HudsonTestCase { + + private static final String UniqueNameForTest = "unique-name-to-test-name-transformer"; + + @Extension + public static class TestTransformer extends TestNameTransformer { + @Override + public String transformName(String name) { + if (UniqueNameForTest.equals(name)) { + return name + "-transformed"; + } + return name; + } + } + + public void testNameIsTransformed() { + assertEquals(UniqueNameForTest + "-transformed", TestNameTransformer.getTransformedName(UniqueNameForTest)); + } + +} + diff --git a/test/src/test/java/hudson/tasks/junit/TestResultPublishingTest.java b/test/src/test/java/hudson/tasks/junit/TestResultPublishingTest.java index 8b2c67151d..ecbaefac14 100644 --- a/test/src/test/java/hudson/tasks/junit/TestResultPublishingTest.java +++ b/test/src/test/java/hudson/tasks/junit/TestResultPublishingTest.java @@ -286,7 +286,7 @@ public class TestResultPublishingTest extends HudsonTestCase { } void assertPaneDiffText(String msg, int expectedValue, Object paneObj) { - assertTrue( "paneObj should be an HtmlElement", paneObj instanceof HtmlElement ); + assertTrue( "paneObj should be an HtmlElement, it was " + paneObj.getClass(), paneObj instanceof HtmlElement ); String paneText = ((HtmlElement) paneObj).asText(); if (expectedValue==0) { assertStringEmptyOrNull(msg, paneText); From 53d1e20f6252228c8fbe58c0fa24e92937122fa2 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 2 May 2013 14:55:06 -0400 Subject: [PATCH 061/233] If an optional component cannot be loaded, print a polite one-line message, not a big scary stack trace. (To reproduce: BuildNowTextPropertyTest from cloudbees-template warns about FolderProxyGroupContainer.) --- .../src/main/java/hudson/ExtensionFinder.java | 31 ++++++++++++++----- 1 file changed, 24 insertions(+), 7 deletions(-) diff --git a/core/src/main/java/hudson/ExtensionFinder.java b/core/src/main/java/hudson/ExtensionFinder.java index 72169a1791..c63c948898 100644 --- a/core/src/main/java/hudson/ExtensionFinder.java +++ b/core/src/main/java/hudson/ExtensionFinder.java @@ -413,7 +413,14 @@ public abstract class ExtensionFinder implements ExtensionPoint { * This is necessary as a failure to load one plugin shouldn't fail the startup of the entire Jenkins. * Instead, we should just drop the failing plugins. */ - public static final Scope FAULT_TOLERANT_SCOPE = new Scope() { + public static final Scope FAULT_TOLERANT_SCOPE = new FaultTolerantScope(true); + private static final Scope QUIET_FAULT_TOLERANT_SCOPE = new FaultTolerantScope(false); + + private static final class FaultTolerantScope implements Scope { + private final boolean verbose; + FaultTolerantScope(boolean verbose) { + this.verbose = verbose; + } public Provider scope(final Key key, final Provider unscoped) { final Provider base = Scopes.SINGLETON.scope(key,unscoped); return new Provider() { @@ -421,13 +428,21 @@ public abstract class ExtensionFinder implements ExtensionPoint { try { return base.get(); } catch (Exception e) { - LOGGER.log(Level.WARNING,"Failed to instantiate. Skipping this component",e); + error(key, e); return null; } catch (LinkageError e) { - LOGGER.log(Level.WARNING,"Failed to instantiate. Skipping this component",e); + error(key, e); return null; } } + void error(Key key, Throwable x) { + if (verbose) { + LOGGER.log(Level.WARNING, "Failed to instantiate " + key + "; skipping this component", x); + } else { + LOGGER.log(Level.WARNING, "Failed to instantiate optional component {0}; skipping", key.getTypeLiteral()); + LOGGER.log(Level.FINE, key.toString(), x); + } + } }; } }; @@ -484,16 +499,18 @@ public abstract class ExtensionFinder implements ExtensionPoint { for (final IndexItem item : index) { id++; + boolean optional = isOptional(item.annotation()); try { AnnotatedElement e = item.element(); Annotation a = item.annotation(); if (!isActive(a,e)) continue; + Scope scope = optional ? QUIET_FAULT_TOLERANT_SCOPE : FAULT_TOLERANT_SCOPE; if (e instanceof Class) { Key key = Key.get((Class)e); resolve((Class)e); annotations.put(key,a); - bind(key).in(FAULT_TOLERANT_SCOPE); + bind(key).in(scope); } else { Class extType; if (e instanceof Field) { @@ -513,15 +530,15 @@ public abstract class ExtensionFinder implements ExtensionPoint { public Object get() { return instantiate(item); } - }).in(FAULT_TOLERANT_SCOPE); + }).in(scope); } } catch (LinkageError e) { // sometimes the instantiation fails in an indirect classloading failure, // which results in a LinkageError - LOGGER.log(isOptional(item.annotation()) ? Level.FINE : Level.WARNING, + LOGGER.log(optional ? Level.FINE : Level.WARNING, "Failed to load "+item.className(), e); } catch (InstantiationException e) { - LOGGER.log(isOptional(item.annotation()) ? Level.FINE : Level.WARNING, + LOGGER.log(optional ? Level.FINE : Level.WARNING, "Failed to load "+item.className(), e); } } From 91f0352ea21a1ebd75b51ad084c47642690e3b2a Mon Sep 17 00:00:00 2001 From: imod Date: Sat, 4 May 2013 17:35:40 +0200 Subject: [PATCH 062/233] try using defaulting of dropdownDescriptorSelector --- core/src/main/java/hudson/tasks/Maven.java | 18 ++++++++++++------ .../resources/hudson/tasks/Maven/config.jelly | 5 +++-- 2 files changed, 15 insertions(+), 8 deletions(-) diff --git a/core/src/main/java/hudson/tasks/Maven.java b/core/src/main/java/hudson/tasks/Maven.java index cf77905fa3..c2fe89b465 100644 --- a/core/src/main/java/hudson/tasks/Maven.java +++ b/core/src/main/java/hudson/tasks/Maven.java @@ -38,8 +38,6 @@ import hudson.model.Computer; import hudson.model.EnvironmentSpecific; import hudson.model.Node; import jenkins.model.Jenkins; -import jenkins.mvn.DefaultGlobalSettingsProvider; -import jenkins.mvn.DefaultSettingsProvider; import jenkins.mvn.GlobalMavenConfig; import jenkins.mvn.GlobalSettingsProvider; import jenkins.mvn.SettingsProvider; @@ -130,13 +128,13 @@ public class Maven extends Builder { * Provides access to the settings.xml to be used for a build. * @since 1.491 */ - private SettingsProvider settings = new DefaultSettingsProvider(); + private SettingsProvider settings; /** * Provides access to the global settings.xml to be used for a build. * @since 1.491 */ - private GlobalSettingsProvider globalSettings = new DefaultGlobalSettingsProvider(); + private GlobalSettingsProvider globalSettings; private final static String MAVEN_1_INSTALLATION_COMMON_FILE = "bin/maven"; private final static String MAVEN_2_INSTALLATION_COMMON_FILE = "bin/mvn"; @@ -164,8 +162,8 @@ public class Maven extends Builder { this.properties = Util.fixEmptyAndTrim(properties); this.jvmOptions = Util.fixEmptyAndTrim(jvmOptions); this.usePrivateRepository = usePrivateRepository; - this.settings = settings; - this.globalSettings = globalSettings; + this.settings = settings != null ? settings : GlobalMavenConfig.get().getSettingsProvider(); + this.globalSettings = globalSettings != null ? globalSettings : GlobalMavenConfig.get().getGlobalSettingsProvider(); } public String getTargets() { @@ -407,6 +405,14 @@ public class Maven extends Builder { public String getDisplayName() { return Messages.Maven_DisplayName(); } + + public GlobalSettingsProvider getDefaultGlobalSettingsProvider() { + return GlobalMavenConfig.get().getGlobalSettingsProvider(); + } + + public SettingsProvider getDefaultSettingsProvider() { + return GlobalMavenConfig.get().getSettingsProvider(); + } public MavenInstallation[] getInstallations() { return installations; diff --git a/core/src/main/resources/hudson/tasks/Maven/config.jelly b/core/src/main/resources/hudson/tasks/Maven/config.jelly index f08e941d54..adda063149 100644 --- a/core/src/main/resources/hudson/tasks/Maven/config.jelly +++ b/core/src/main/resources/hudson/tasks/Maven/config.jelly @@ -50,7 +50,8 @@ THE SOFTWARE. - + + - + \ No newline at end of file From ad286c5197128e1a625c1a724350ea93b5c406a7 Mon Sep 17 00:00:00 2001 From: imod Date: Sun, 5 May 2013 11:25:51 +0200 Subject: [PATCH 063/233] [FIXED JENKINS-17723] add test cases to verify defaulting global settings providers --- .../java/hudson/maven/MavenProjectTest.java | 28 ++++++++++++++++ .../src/test/java/hudson/tasks/MavenTest.java | 33 +++++++++++++++++++ 2 files changed, 61 insertions(+) diff --git a/test/src/test/java/hudson/maven/MavenProjectTest.java b/test/src/test/java/hudson/maven/MavenProjectTest.java index 5410a2213d..d53a86ecaa 100644 --- a/test/src/test/java/hudson/maven/MavenProjectTest.java +++ b/test/src/test/java/hudson/maven/MavenProjectTest.java @@ -33,6 +33,11 @@ import hudson.tasks.Shell; import java.io.File; import jenkins.model.Jenkins; +import jenkins.mvn.DefaultGlobalSettingsProvider; +import jenkins.mvn.DefaultSettingsProvider; +import jenkins.mvn.FilePathGlobalSettingsProvider; +import jenkins.mvn.FilePathSettingsProvider; +import jenkins.mvn.GlobalMavenConfig; import org.junit.Assert; import org.jvnet.hudson.test.Bug; @@ -209,4 +214,27 @@ public class MavenProjectTest extends HudsonTestCase { assertEquals(r,m.getRunPostStepsIfResult()); } } + + + public void testDefaultSettingsProvider() throws Exception { + { + MavenModuleSet m = createMavenProject(); + + assertNotNull(m); + assertEquals(DefaultSettingsProvider.class, m.getSettings().getClass()); + assertEquals(DefaultGlobalSettingsProvider.class, m.getGlobalSettings().getClass()); + } + + { + GlobalMavenConfig globalMavenConfig = GlobalMavenConfig.get(); + assertNotNull("No global Maven Config available", globalMavenConfig); + globalMavenConfig.setSettingsProvider(new FilePathSettingsProvider("/tmp/settigns.xml")); + globalMavenConfig.setGlobalSettingsProvider(new FilePathGlobalSettingsProvider("/tmp/global-settigns.xml")); + + MavenModuleSet m = createMavenProject(); + assertEquals(FilePathSettingsProvider.class, m.getSettings().getClass()); + assertEquals("/tmp/settigns.xml", ((FilePathSettingsProvider)m.getSettings()).getPath()); + assertEquals("/tmp/global-settigns.xml", ((FilePathGlobalSettingsProvider)m.getGlobalSettings()).getPath()); + } + } } diff --git a/test/src/test/java/hudson/tasks/MavenTest.java b/test/src/test/java/hudson/tasks/MavenTest.java index 7bd442142e..6daf14b6cd 100644 --- a/test/src/test/java/hudson/tasks/MavenTest.java +++ b/test/src/test/java/hudson/tasks/MavenTest.java @@ -26,6 +26,11 @@ package hudson.tasks; import hudson.model.Build; import hudson.model.FreeStyleProject; import jenkins.model.Jenkins; +import jenkins.mvn.DefaultGlobalSettingsProvider; +import jenkins.mvn.DefaultSettingsProvider; +import jenkins.mvn.FilePathGlobalSettingsProvider; +import jenkins.mvn.FilePathSettingsProvider; +import jenkins.mvn.GlobalMavenConfig; import hudson.model.JDK; import hudson.model.ParametersDefinitionProperty; import hudson.model.Result; @@ -47,6 +52,7 @@ import java.util.Collections; import junit.framework.Assert; +import org.apache.maven.settings.building.FileSettingsSource; import org.jvnet.hudson.test.HudsonTestCase; import com.gargoylesoftware.htmlunit.html.HtmlForm; @@ -196,4 +202,31 @@ public class MavenTest extends HudsonTestCase { System.out.println(buildLog); assertFalse(buildLog.contains("-Dpassword=12345")); } + + public void testDefaultSettingsProvider() throws Exception { + { + FreeStyleProject p = createFreeStyleProject(); + p.getBuildersList().add(new Maven("a", null, "a.pom", "c=d", "-e", true)); + + Maven m = p.getBuildersList().get(Maven.class); + assertNotNull(m); + assertEquals(DefaultSettingsProvider.class, m.getSettings().getClass()); + assertEquals(DefaultGlobalSettingsProvider.class, m.getGlobalSettings().getClass()); + } + + { + GlobalMavenConfig globalMavenConfig = GlobalMavenConfig.get(); + assertNotNull("No global Maven Config available", globalMavenConfig); + globalMavenConfig.setSettingsProvider(new FilePathSettingsProvider("/tmp/settigns.xml")); + globalMavenConfig.setGlobalSettingsProvider(new FilePathGlobalSettingsProvider("/tmp/global-settigns.xml")); + + FreeStyleProject p = createFreeStyleProject(); + p.getBuildersList().add(new Maven("b", null, "b.pom", "c=d", "-e", true)); + + Maven m = p.getBuildersList().get(Maven.class); + assertEquals(FilePathSettingsProvider.class, m.getSettings().getClass()); + assertEquals("/tmp/settigns.xml", ((FilePathSettingsProvider)m.getSettings()).getPath()); + assertEquals("/tmp/global-settigns.xml", ((FilePathGlobalSettingsProvider)m.getGlobalSettings()).getPath()); + } + } } From 961f691cf03b0701787eae3506ba7fa18d06279c Mon Sep 17 00:00:00 2001 From: imod Date: Sun, 5 May 2013 17:49:42 +0200 Subject: [PATCH 064/233] [FIXED JENKINS-17858] allow to be defaulting to a specifig instance --- .../main/resources/lib/form/dropdownDescriptorSelector.jelly | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/core/src/main/resources/lib/form/dropdownDescriptorSelector.jelly b/core/src/main/resources/lib/form/dropdownDescriptorSelector.jelly index c68760382f..aad0a87e51 100644 --- a/core/src/main/resources/lib/form/dropdownDescriptorSelector.jelly +++ b/core/src/main/resources/lib/form/dropdownDescriptorSelector.jelly @@ -39,7 +39,8 @@ THE SOFTWARE. If unspecified, inferred from the type of the field. - If specified, this will be chosen as the default value in case the current selection is null. + If specified, this will be chosen as the default value in case the current selection is null. The default can be an specific instance or a descriptor e.g. + ${descriptor.defaultSettingsProvider} or ${descriptor.defaultSettingsProvider.descriptor}. In the later case, the from input fields will be empty. @@ -49,6 +50,7 @@ THE SOFTWARE. + Date: Mon, 6 May 2013 11:31:28 +1000 Subject: [PATCH 065/233] Update changelog.html changelog entry for JENKINS-17723 --- changelog.html | 3 +++ 1 file changed, 3 insertions(+) diff --git a/changelog.html b/changelog.html index b02562a180..b416baf641 100644 --- a/changelog.html +++ b/changelog.html @@ -55,6 +55,9 @@ Upcoming changes diff --git a/war/src/main/webapp/help/view-config/description.html b/war/src/main/webapp/help/view-config/description.html index 729a99facd..0975f06775 100644 --- a/war/src/main/webapp/help/view-config/description.html +++ b/war/src/main/webapp/help/view-config/description.html @@ -1,5 +1,5 @@
          This message will be displayed on the view page. Useful for describing what this view is about, or linking to relevant resources. - Can contain HTML tags. -
          \ No newline at end of file + Can contain HTML tags or whatever markup language is defined for the system. + From a5f673207e04c4e2a3a74d6ab9818e5b57bf29f0 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sat, 18 May 2013 19:09:32 -0700 Subject: [PATCH 098/233] Fixed a broken build caused by OutOfMemoryError It looks like our tests are getting bigger to the point that it needs more PermGen space. Use fork and run with a bigger perm gen size to get going. --- core/pom.xml | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/core/pom.xml b/core/pom.xml index b49205a10a..e2f840662f 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -749,6 +749,14 @@ THE SOFTWARE. + + maven-surefire-plugin + + 0.5C + true + -XX:MaxPermSize=128m + + maven-jar-plugin From 3a4b88ff1e65e3fd56dd00a9e9409912e370a63b Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sat, 18 May 2013 21:05:33 -0700 Subject: [PATCH 099/233] [maven-release-plugin] prepare release jenkins-1.515 --- cli/pom.xml | 2 +- core/pom.xml | 2 +- maven-plugin/pom.xml | 2 +- plugins/pom.xml | 12 ++++++------ pom.xml | 2 +- test/pom.xml | 2 +- ui-samples-plugin/pom.xml | 2 +- war/pom.xml | 2 +- 8 files changed, 13 insertions(+), 13 deletions(-) diff --git a/cli/pom.xml b/cli/pom.xml index ac41da3103..4c690fcf68 100644 --- a/cli/pom.xml +++ b/cli/pom.xml @@ -5,7 +5,7 @@ pom org.jenkins-ci.main - 1.515-SNAPSHOT + 1.515 cli diff --git a/core/pom.xml b/core/pom.xml index e2f840662f..5791080974 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.515-SNAPSHOT + 1.515 ../pom.xml diff --git a/maven-plugin/pom.xml b/maven-plugin/pom.xml index c6d5e29e01..417c4ba9b8 100644 --- a/maven-plugin/pom.xml +++ b/maven-plugin/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.515-SNAPSHOT + 1.515 maven-plugin diff --git a/plugins/pom.xml b/plugins/pom.xml index 8d75f27433..fee5069129 100644 --- a/plugins/pom.xml +++ b/plugins/pom.xml @@ -11,7 +11,7 @@ org.jenkins-ci.plugins plugin Jenkins plugin POM - 1.515-SNAPSHOT + 1.515 pom org.jenkins-ci.main maven-plugin - 1.515-SNAPSHOT + 1.515 @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.515-SNAPSHOT + 1.515 test org.jenkins-ci.main jenkins-core - 1.515-SNAPSHOT + 1.515 provided org.jenkins-ci.main jenkins-test-harness - 1.515-SNAPSHOT + 1.515 test org.jenkins-ci.main ui-samples-plugin - 1.515-SNAPSHOT + 1.515 test org.jenkins-ci.main maven-plugin - 1.515 + 1.516-SNAPSHOT @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.515 + 1.516-SNAPSHOT test org.jenkins-ci.main jenkins-core - 1.515 + 1.516-SNAPSHOT provided org.jenkins-ci.main jenkins-test-harness - 1.515 + 1.516-SNAPSHOT test org.jenkins-ci.main ui-samples-plugin - 1.515 + 1.516-SNAPSHOT test +

          What's new in 1.515 (2013/05/18)

          • Windows services now auto-restart in case of abnormal process termination. @@ -90,7 +93,6 @@ Upcoming changes Allow the combination filter to accept parameter values. (issue 7285)
          -

          What's new in 1.514 (2013/05/01)

          • From 8062be49ac9953aff41d4458e34e3caa0d797632 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sat, 18 May 2013 21:57:35 -0700 Subject: [PATCH 102/233] updated changelog as a part of the release --- debian/debian/changelog | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/debian/debian/changelog b/debian/debian/changelog index 9db182f2e9..330d8d700c 100644 --- a/debian/debian/changelog +++ b/debian/debian/changelog @@ -1,3 +1,9 @@ +jenkins (1.515) unstable; urgency=low + + * See http://jenkins-ci.org/changelog for more details. + + -- Kohsuke Kawaguchi Sat, 18 May 2013 21:29:37 -0700 + jenkins (1.514) unstable; urgency=low * See http://jenkins-ci.org/changelog for more details. From 5fa9db8f2cbab330f465098ad17f0a6cfc769a54 Mon Sep 17 00:00:00 2001 From: Johnbo Date: Mon, 20 May 2013 18:50:07 +0300 Subject: [PATCH 103/233] Update Messages_es.properties Correct spelling --- .../hudson/maven/Messages_es.properties | 28 +++++++++---------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/maven-plugin/src/main/resources/hudson/maven/Messages_es.properties b/maven-plugin/src/main/resources/hudson/maven/Messages_es.properties index ac2706e49e..68c6a1d396 100644 --- a/maven-plugin/src/main/resources/hudson/maven/Messages_es.properties +++ b/maven-plugin/src/main/resources/hudson/maven/Messages_es.properties @@ -20,41 +20,41 @@ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. -MavenBuild.FailedEarlier=La ejecución falló antes de llegar a este módulo +MavenBuild.FailedEarlier=La ejecuciĂłn fallĂł antes de llegar a este mĂłdulo MavenBuild.KeptBecauseOfParent=Mantener porque {0} se mantiene -MavenBuild.Triggering=Lanzando la ejecución de {0} +MavenBuild.Triggering=Lanzando la ejecuciĂłn de {0} MavenBuilder.Aborted=Cancelado -MavenBuilder.AsyncFailed=La ejecución asincrona ha fallado +MavenBuilder.AsyncFailed=La ejecuciĂłn asincrona ha fallado MavenBuilder.Failed=Maven ha acabado con error -MavenBuilder.Waiting=Esperando a que Jenkins finalize de recopilar datos +MavenBuilder.Waiting=Esperando a que Jenkins finalice de recopilar datos MavenModule.Pronoun=Modulo MavenModuleSet.DiplayName=Crear un proyecto maven2/3 -MavenModuleSetBuild.DiscoveredModule=Se ha descubierto un nuevo módulo {0} {1} +MavenModuleSetBuild.DiscoveredModule=Se ha descubierto un nuevo mĂłdulo {0} {1} MavenModuleSetBuild.FailedToParsePom=Error al analizar el fichero POM -MavenModuleSetBuild.NoSuchPOMFile=No existe el fichero {0}\nQuizas sea necesario que especifiques la ubicación del fichero POM -MavenModuleSetBuild.NoSuchAlternateSettings=No existe el fichero de configuración {0} \nVerifica que se ha especificado un fichero en la configuración, y que dicho fichero existe el el espacio de trabajo. -MavenModuleSetBuild.NoMavenInstall=Se necesita una instalación de ''maven'' para poder ejecutar este proyecto.\nEs posible que no se haya especificado dónde está la instalación de maven o sea incorrecta. +MavenModuleSetBuild.NoSuchPOMFile=No existe el fichero {0}\nQuizas sea necesario que especifiques la ubicaciĂłn del fichero POM +MavenModuleSetBuild.NoSuchAlternateSettings=No existe el fichero de configuraciĂłn {0} \nVerifica que se ha especificado un fichero en la configuraciĂłn, y que dicho fichero existe el el espacio de trabajo. +MavenModuleSetBuild.NoMavenInstall=Se necesita una instalaciĂłn de ''maven'' para poder ejecutar este proyecto.\nEs posible que no se haya especificado dĂłnde estĂĄ la instalaciĂłn de maven o que sea incorrecta. MavenProbeAction.DisplayName=Monitorizar proceso maven -MavenProcessFactory.ClassWorldsNotFound=No se encontró la libraría classworlds*.jar en {0} -- żEs un directorio de instalación de maven válido? +MavenProcessFactory.ClassWorldsNotFound=No se encontrĂł la librerĂ­a classworlds*.jar en {0} -- ÂżEs un directorio de instalaciĂłn de maven vĂĄlido? MavenRedeployer.DisplayName=Desplegar al repositorio maven. ProcessCache.Reusing=Reutilizar un proceso existente de maven RedeployPublisher.getDisplayName=Desplegar ficheros al repositorio maven -ReleaseAction.DisplayName=Publicar una nueva versión +ReleaseAction.DisplayName=Publicar una nueva versiĂłn RedeployPublisher.RepositoryURL.Mandatory=La URL del repositorio es obligatoria -MavenModuleSet.AlternateSettingsRelativePath=El fichero de configuración alternativo debe tener una ruta relativa. +MavenModuleSet.AlternateSettingsRelativePath=El fichero de configuraciĂłn alternativo debe tener una ruta relativa. MavenVersionCallable.MavenHomeDoesntExist=El directorio ''HOME'' de maven no existe {0} MavenModuleSetBuild.SettinsgXmlAndPrivateRepository=Usando el fichero settings.xml en {0} y el repositorio privado en {1} -MavenModuleSetBuild.NoMavenConfigured=Es necesaria una instalación de maven para poder ejecutar este proyecto. \ - Puede ocurrir que no haya ninguna versión de maven en el servidor, o que su proyecto tenga configurada una versión específica de maven. +MavenModuleSetBuild.NoMavenConfigured=Es necesaria una instalaciĂłn de maven para poder ejecutar este proyecto. \ + Puede ocurrir que no haya ninguna versiĂłn de maven en el servidor, o que su proyecto tenga configurada una versiĂłn especĂ­fica de maven. MavenModuleSetBuild.DownloadedArtifact=Artefacto {0}/{1} descargado -MavenModuleSetBuild.FoundModuleWithoutProject=Se ha encontrado un módulo en la ubicación {0} pero no un proyecto asociado. +MavenModuleSetBuild.FoundModuleWithoutProject=Se ha encontrado un mĂłdulo en la ubicaciĂłn {0} pero no un proyecto asociado. MavenVersionCallable.MavenHomeIsNotDirectory=La variable ''HOME'' de maven no es un directorio MavenModuleSetBuild.FailedToTransfer=Error al transferir {0} From ab2774362f1d5a5510b99a4b8f02236e8ca23d6c Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Mon, 20 May 2013 13:04:27 -0400 Subject: [PATCH 104/233] [JENKINS-15652] Include directory in assertion messages so it is possible to tell which project is broken. --- .../jenkins/model/lazy/AbstractLazyLoadRunMap.java | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java b/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java index c81c4d4e80..92a6100fa6 100644 --- a/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java +++ b/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java @@ -436,8 +436,8 @@ public abstract class AbstractLazyLoadRunMap extends AbstractMap i // assertion error, but we are so far unable to get to the bottom of this bug. // but don't let this kill the loading the hard way String msg = String.format( - "Assertion error: failing to load #%d %s: lo=%d,hi=%d,size=%d,size2=%d", - n, d, lo, hi, idOnDisk.size(), initialSize); + "JENKINS-15652 Assertion error: failing to load %s #%d %s: lo=%d,hi=%d,size=%d,size2=%d", + dir, n, d, lo, hi, idOnDisk.size(), initialSize); LOGGER.log(Level.WARNING, msg,new Exception()); throw new ArrayIndexOutOfBoundsException(msg); } @@ -448,8 +448,8 @@ public abstract class AbstractLazyLoadRunMap extends AbstractMap i // assertion error, but we are so far unable to get to the bottom of this bug. // but don't let this kill the loading the hard way String msg = String.format( - "Assertion error: failing to load #%d %s: lo=%d,hi=%d,pivot=%d,size=%d (initial:lo=%d,hi=%d,size=%d)", - n, d, lo, hi, pivot, idOnDisk.size(), initialLo, initialHi, initialSize); + "JENKINS-15652Assertion error: failing to load %s #%d %s: lo=%d,hi=%d,pivot=%d,size=%d (initial:lo=%d,hi=%d,size=%d)", + dir, n, d, lo, hi, pivot, idOnDisk.size(), initialLo, initialHi, initialSize); LOGGER.log(Level.WARNING, msg,new Exception()); throw new ArrayIndexOutOfBoundsException(msg); } @@ -489,8 +489,8 @@ public abstract class AbstractLazyLoadRunMap extends AbstractMap i // assertion error, but we are so far unable to get to the bottom of this bug. // but don't let this kill the loading the hard way LOGGER.log(Level.WARNING, String.format( - "Assertion error: failing to load #%d %s: lo=%d,hi=%d,size=%d (initial:lo=%d,hi=%d,size=%d)", - n,d,lo,hi,idOnDisk.size(), initialLo,initialHi,initialSize),new Exception()); + "JENKINS-15652 Assertion error: failing to load %s #%d %s: lo=%d,hi=%d,size=%d (initial:lo=%d,hi=%d,size=%d)", + dir, n,d,lo,hi,idOnDisk.size(), initialLo,initialHi,initialSize),new Exception()); return null; } return getById(idOnDisk.get(lo-1)); From df53cc7d7262c6f7f3f3badab93b7f2ba4ac9ae5 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Mon, 20 May 2013 13:27:19 -0400 Subject: [PATCH 105/233] Lack of HTML escape made Javadoc misleading. --- .../main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java b/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java index 92a6100fa6..55fc64950c 100644 --- a/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java +++ b/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java @@ -350,7 +350,7 @@ public abstract class AbstractLazyLoadRunMap extends AbstractMap i * defines what we mean by "nearby" above. * If EXACT, find #N or return null. * If ASC, finds the closest #M that satisfies M>=N. - * If DESC, finds the closest #M that satisfies M<=N. + * If DESC, finds the closest #M that satisfies M<=N. */ public R search(final int n, final Direction d) { Entry> c = index.ceilingEntry(n); From 8835bdc13bf575de479ccb75ed682b72fea298a4 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Mon, 20 May 2013 12:25:11 -0700 Subject: [PATCH 106/233] creating an RC branch --- changelog.html | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/changelog.html b/changelog.html index fa3760eede..044e2e3a1c 100644 --- a/changelog.html +++ b/changelog.html @@ -54,6 +54,14 @@ Upcoming changes + + + - - -

            What's new in 1.515 (2013/05/18)

              From 3e66acc7eb7020a9dad2fe33d782b1d1b5a6414f Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Mon, 20 May 2013 12:25:15 -0700 Subject: [PATCH 107/233] the trunk is toward 1.517-SNAPSHOT --- cli/pom.xml | 2 +- core/pom.xml | 2 +- maven-plugin/pom.xml | 2 +- plugins/pom.xml | 12 ++++++------ pom.xml | 2 +- test/pom.xml | 2 +- ui-samples-plugin/pom.xml | 2 +- war/pom.xml | 2 +- 8 files changed, 13 insertions(+), 13 deletions(-) diff --git a/cli/pom.xml b/cli/pom.xml index e0dca53c38..3df7ad60d5 100644 --- a/cli/pom.xml +++ b/cli/pom.xml @@ -5,7 +5,7 @@ pom org.jenkins-ci.main - 1.516-SNAPSHOT + 1.517-SNAPSHOT cli diff --git a/core/pom.xml b/core/pom.xml index a5636bf7d8..0bd738476d 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.516-SNAPSHOT + 1.517-SNAPSHOT ../pom.xml diff --git a/maven-plugin/pom.xml b/maven-plugin/pom.xml index 298856a700..bdc90e285c 100644 --- a/maven-plugin/pom.xml +++ b/maven-plugin/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.516-SNAPSHOT + 1.517-SNAPSHOT maven-plugin diff --git a/plugins/pom.xml b/plugins/pom.xml index 7275ce48bc..1826e1b805 100644 --- a/plugins/pom.xml +++ b/plugins/pom.xml @@ -11,7 +11,7 @@ org.jenkins-ci.plugins plugin Jenkins plugin POM - 1.516-SNAPSHOT + 1.517-SNAPSHOT pom org.jenkins-ci.main maven-plugin - 1.516-SNAPSHOT + 1.517-SNAPSHOT @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.516-SNAPSHOT + 1.517-SNAPSHOT test org.jenkins-ci.main jenkins-core - 1.516-SNAPSHOT + 1.517-SNAPSHOT provided org.jenkins-ci.main jenkins-test-harness - 1.516-SNAPSHOT + 1.517-SNAPSHOT test org.jenkins-ci.main ui-samples-plugin - 1.516-SNAPSHOT + 1.517-SNAPSHOT test diff --git a/core/src/main/java/hudson/Functions.java b/core/src/main/java/hudson/Functions.java index be9c3b526e..d922f3310e 100644 --- a/core/src/main/java/hudson/Functions.java +++ b/core/src/main/java/hudson/Functions.java @@ -1724,7 +1724,7 @@ public class Functions { * to wrap line before any sequence of punctuation characters or anywhere * in the middle of prolonged sequences of word characters. * - * @since 1.516 + * @since 1.517 */ public static String breakableString(final String plain) { diff --git a/core/src/main/resources/lib/layout/breakable.jelly b/core/src/main/resources/lib/layout/breakable.jelly index 7e1c66bdbe..956bb389c5 100644 --- a/core/src/main/resources/lib/layout/breakable.jelly +++ b/core/src/main/resources/lib/layout/breakable.jelly @@ -26,6 +26,7 @@ THE SOFTWARE. Send escaped value to output decorated to be safely broken into lines when necessary + @since 1.517 Unescaped value to output diff --git a/core/src/test/java/hudson/FunctionsTest.java b/core/src/test/java/hudson/FunctionsTest.java index 3ef3014d64..6a7ec2bff6 100644 --- a/core/src/test/java/hudson/FunctionsTest.java +++ b/core/src/test/java/hudson/FunctionsTest.java @@ -264,6 +264,7 @@ public class FunctionsTest { } } + @Bug(17030) @Test public void testBreakableString() { From 51fbd2d8675fb3703ce38d935e661abf03e1b83b Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 21 May 2013 17:41:39 -0400 Subject: [PATCH 110/233] [JENKINS-16301] Replace impl of getDigestOf with standard (Commons Codec) DigestUtils.md5Hex, for simplicity. --- core/src/main/java/hudson/Util.java | 22 +++------------------- 1 file changed, 3 insertions(+), 19 deletions(-) diff --git a/core/src/main/java/hudson/Util.java b/core/src/main/java/hudson/Util.java index 511d9eefa8..696bfe5f64 100644 --- a/core/src/main/java/hudson/Util.java +++ b/core/src/main/java/hudson/Util.java @@ -30,11 +30,9 @@ import edu.umd.cs.findbugs.annotations.SuppressWarnings; import hudson.Proc.LocalProc; import hudson.model.TaskListener; import hudson.os.PosixAPI; -import hudson.util.IOException2; import hudson.util.QuotedStringTokenizer; import hudson.util.VariableResolver; import hudson.util.jna.WinIOException; -import jenkins.model.Jenkins; import org.apache.commons.io.IOUtils; import org.apache.commons.lang.time.FastDateFormat; import org.apache.tools.ant.BuildException; @@ -45,7 +43,6 @@ import org.apache.tools.ant.types.FileSet; import org.jruby.ext.posix.FileStat; import org.jruby.ext.posix.POSIX; import org.codehaus.mojo.animal_sniffer.IgnoreJRERequirement; -import org.kohsuke.stapler.Stapler; import javax.crypto.SecretKey; import javax.crypto.spec.SecretKeySpec; @@ -61,7 +58,6 @@ import java.nio.CharBuffer; import java.nio.charset.CharacterCodingException; import java.nio.charset.Charset; import java.nio.charset.CharsetEncoder; -import java.security.DigestInputStream; import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; import java.text.NumberFormat; @@ -76,6 +72,7 @@ import java.util.regex.Pattern; import hudson.util.jna.Kernel32Utils; import static hudson.util.jna.GNUCLibrary.LIBC; +import org.apache.commons.codec.digest.DigestUtils; /** * Various utility methods that don't have more proper home. @@ -554,23 +551,10 @@ public class Util { * The stream will be closed by this method at the end of this method. * @return * 32-char wide string + * @see DigestUtils#md5(InputStream) */ public static String getDigestOf(InputStream source) throws IOException { - try { - MessageDigest md5 = MessageDigest.getInstance("MD5"); - - byte[] buffer = new byte[1024]; - DigestInputStream in =new DigestInputStream(source,md5); - try { - while(in.read(buffer)>=0) - ; // simply discard the input - } finally { - in.close(); - } - return toHexString(md5.digest()); - } catch (NoSuchAlgorithmException e) { - throw new IOException2("MD5 not installed",e); // impossible - } + return DigestUtils.md5Hex(source); } public static String getDigestOf(String text) { From 9d72311ba0222b9d0489605b8ec2cec711690993 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 21 May 2013 17:42:50 -0400 Subject: [PATCH 111/233] [JENKINS-16301] Use a buffered input stream to get somewhat better performance. --- core/src/main/java/hudson/FilePath.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/core/src/main/java/hudson/FilePath.java b/core/src/main/java/hudson/FilePath.java index 3dabd48108..cee15b41a7 100644 --- a/core/src/main/java/hudson/FilePath.java +++ b/core/src/main/java/hudson/FilePath.java @@ -97,6 +97,7 @@ import java.util.zip.GZIPInputStream; import com.sun.jna.Native; import hudson.os.PosixException; +import java.io.BufferedInputStream; import java.util.Enumeration; import java.util.logging.Logger; import org.apache.tools.ant.taskdefs.Chmod; @@ -1663,7 +1664,7 @@ public final class FilePath implements Serializable { return act(new FileCallable() { private static final long serialVersionUID = 1L; public String invoke(File f, VirtualChannel channel) throws IOException { - return Util.getDigestOf(new FileInputStream(f)); + return Util.getDigestOf(new BufferedInputStream(new FileInputStream(f))); } }); } From 07280edc95a1341128ba949626b834055a2933fe Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 21 May 2013 19:19:27 -0400 Subject: [PATCH 112/233] JUnit 4. --- .../test/java/hudson/model/FingerprintTest.java | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/core/src/test/java/hudson/model/FingerprintTest.java b/core/src/test/java/hudson/model/FingerprintTest.java index 2c1cbbdc71..723af3aabc 100644 --- a/core/src/test/java/hudson/model/FingerprintTest.java +++ b/core/src/test/java/hudson/model/FingerprintTest.java @@ -23,14 +23,16 @@ */ package hudson.model; -import junit.framework.TestCase; import hudson.model.Fingerprint.RangeSet; +import static org.junit.Assert.*; +import org.junit.Test; /** * @author Kohsuke Kawaguchi */ -public class FingerprintTest extends TestCase { - public void test() { +public class FingerprintTest { + + @Test public void rangeSet() { RangeSet rs = new RangeSet(); assertFalse(rs.includes(0)); assertFalse(rs.includes(3)); @@ -62,7 +64,7 @@ public class FingerprintTest extends TestCase { assertEquals("[3,7),[9,11)",rs.toString()); } - public void testMerge() { + @Test public void merge() { RangeSet x = new RangeSet(); x.add(1); x.add(2); @@ -81,7 +83,7 @@ public class FingerprintTest extends TestCase { assertEquals("[1,7)",x.toString()); } - public void testMerge2() { + @Test public void merge2() { RangeSet x = new RangeSet(); x.add(1); x.add(2); @@ -98,7 +100,7 @@ public class FingerprintTest extends TestCase { assertEquals("[1,7)",x.toString()); } - public void testMerge3() { + @Test public void merge3() { RangeSet x = new RangeSet(); x.add(1); x.add(5); From 8d2e4523368716c82dc7333b4357d21d0dc93526 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 21 May 2013 21:39:44 -0400 Subject: [PATCH 113/233] [JENKINS-16301] Verifying current serial format as a baseline. --- .../main/java/hudson/model/Fingerprint.java | 25 ++++++++++++++++--- .../main/java/hudson/util/PersistedList.java | 4 +++ .../java/hudson/model/FingerprintTest.java | 13 ++++++++++ .../resources/hudson/model/fingerprint.xml | 21 ++++++++++++++++ 4 files changed, 59 insertions(+), 4 deletions(-) create mode 100644 core/src/test/resources/hudson/model/fingerprint.xml diff --git a/core/src/main/java/hudson/model/Fingerprint.java b/core/src/main/java/hudson/model/Fingerprint.java index ab6989ba09..075fcf9533 100644 --- a/core/src/main/java/hudson/model/Fingerprint.java +++ b/core/src/main/java/hudson/model/Fingerprint.java @@ -24,11 +24,11 @@ package hudson.model; import com.google.common.collect.ImmutableList; -import com.google.common.collect.ImmutableListMultimap; import com.thoughtworks.xstream.XStream; import com.thoughtworks.xstream.converters.Converter; import com.thoughtworks.xstream.converters.MarshallingContext; import com.thoughtworks.xstream.converters.UnmarshallingContext; +import com.thoughtworks.xstream.converters.basic.DateConverter; import com.thoughtworks.xstream.converters.collections.CollectionConverter; import com.thoughtworks.xstream.io.HierarchicalStreamReader; import com.thoughtworks.xstream.io.HierarchicalStreamWriter; @@ -61,6 +61,7 @@ import java.util.Hashtable; import java.util.Iterator; import java.util.List; import java.util.Map.Entry; +import java.util.TreeMap; import java.util.logging.Level; import java.util.logging.Logger; @@ -180,6 +181,10 @@ public class Fingerprint implements ModelObject, Saveable { return false; } + + @Override public String toString() { + return name + " #" + number; + } } /** @@ -581,11 +586,15 @@ public class Fingerprint implements ModelObject, Saveable { private transient volatile List transientFacets = null; public Fingerprint(Run build, String fileName, byte[] md5sum) throws IOException { - this.original = build==null ? null : new BuildPtr(build); + this(build==null ? null : new BuildPtr(build), fileName, md5sum); + save(); + } + + Fingerprint(BuildPtr original, String fileName, byte[] md5sum) { + this.original = original; this.md5sum = md5sum; this.fileName = fileName; this.timestamp = new Date(); - save(); } /** @@ -838,13 +847,17 @@ public class Fingerprint implements ModelObject, Saveable { start = System.currentTimeMillis(); File file = getFingerprintFile(md5sum); - getConfigFile(file).write(this); + save(file); SaveableListener.fireOnChange(this, getConfigFile(file)); if(logger.isLoggable(Level.FINE)) logger.fine("Saving fingerprint "+file+" took "+(System.currentTimeMillis()-start)+"ms"); } + void save(File file) throws IOException { + getConfigFile(file).write(this); + } + /** * Update references to a renamed job in the fingerprint */ @@ -932,6 +945,10 @@ public class Fingerprint implements ModelObject, Saveable { } } + @Override public String toString() { + return "Fingerprint[original=" + original + ",hash=" + getHashString() + ",fileName=" + fileName + ",timestamp=" + new DateConverter().toString(timestamp) + ",usages=" + new TreeMap(usages) + ",facets=" + facets + "]"; + } + private static final XStream XSTREAM = new XStream2(); static { XSTREAM.alias("fingerprint",Fingerprint.class); diff --git a/core/src/main/java/hudson/util/PersistedList.java b/core/src/main/java/hudson/util/PersistedList.java index 52d20a3caf..89325d0c05 100644 --- a/core/src/main/java/hudson/util/PersistedList.java +++ b/core/src/main/java/hudson/util/PersistedList.java @@ -193,6 +193,10 @@ public class PersistedList implements Iterable { return data.contains(item); } + @Override public String toString() { + return toList().toString(); + } + /** * {@link Converter} implementation for XStream. * diff --git a/core/src/test/java/hudson/model/FingerprintTest.java b/core/src/test/java/hudson/model/FingerprintTest.java index 723af3aabc..eaa01473d3 100644 --- a/core/src/test/java/hudson/model/FingerprintTest.java +++ b/core/src/test/java/hudson/model/FingerprintTest.java @@ -24,6 +24,7 @@ package hudson.model; import hudson.model.Fingerprint.RangeSet; +import java.io.File; import static org.junit.Assert.*; import org.junit.Test; @@ -115,4 +116,16 @@ public class FingerprintTest { x.add(y); assertEquals("[1,2),[3,4),[5,6),[7,8)",x.toString()); } + + @Test public void deserialize() throws Exception { + assertEquals("Fingerprint[" + + "original=stapler/org.kohsuke.stapler:stapler-jelly #123," + + "hash=069484c9e963cc615c51278327da8eab," + + "fileName=org.kohsuke.stapler:stapler-jelly-1.207.jar," + + "timestamp=2013-05-21 19:20:03.534 UTC," + + "usages={stuff=[304,306),[307,324),[328,330), stuff/test:stuff=[2,67),[72,77),[84,223),[228,229),[232,268)}," + + "facets=[]]", + Fingerprint.load(new File(FingerprintTest.class.getResource("fingerprint.xml").toURI())).toString()); + } + } diff --git a/core/src/test/resources/hudson/model/fingerprint.xml b/core/src/test/resources/hudson/model/fingerprint.xml new file mode 100644 index 0000000000..dc933bcc3d --- /dev/null +++ b/core/src/test/resources/hudson/model/fingerprint.xml @@ -0,0 +1,21 @@ + + + 2013-05-21 19:20:03.534 UTC + + stapler/org.kohsuke.stapler:stapler-jelly + 123 + + 069484c9e963cc615c51278327da8eab + org.kohsuke.stapler:stapler-jelly-1.207.jar + + + stuff/test:stuff + 2-66,72-76,84-222,228,232-267 + + + stuff + 304-305,307-323,328-329 + + + + \ No newline at end of file From 4b8329a1c4f804c672491e77e84a882785bb7941 Mon Sep 17 00:00:00 2001 From: Ari Hyttinen Date: Wed, 22 May 2013 12:39:31 +0300 Subject: [PATCH 114/233] Fixed reporting correct pass count by TestResult.toPrettyString() method. --- core/src/main/java/hudson/tasks/test/TestResult.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/main/java/hudson/tasks/test/TestResult.java b/core/src/main/java/hudson/tasks/test/TestResult.java index 98b069eda6..ebf7515946 100644 --- a/core/src/main/java/hudson/tasks/test/TestResult.java +++ b/core/src/main/java/hudson/tasks/test/TestResult.java @@ -246,7 +246,7 @@ public abstract class TestResult extends TestObject { sb.append("Total Count: ").append(this.getTotalCount()).append(", "); sb.append("Fail: ").append(this.getFailCount()).append(", "); sb.append("Skipt: ").append(this.getSkipCount()).append(", "); - sb.append("Pass: ").append(this.getSkipCount()).append(",\n"); + sb.append("Pass: ").append(this.getPassCount()).append(",\n"); sb.append("Test Result Class: " ).append(this.getClass().getName()).append(" }\n"); return sb.toString(); } From 6c1c5cc4903a957ed5b107522fa3411ff47d95db Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 22 May 2013 09:44:45 -0400 Subject: [PATCH 115/233] Was missing. --- ui-samples-plugin/src/main/resources/index.jelly | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 ui-samples-plugin/src/main/resources/index.jelly diff --git a/ui-samples-plugin/src/main/resources/index.jelly b/ui-samples-plugin/src/main/resources/index.jelly new file mode 100644 index 0000000000..298c582a97 --- /dev/null +++ b/ui-samples-plugin/src/main/resources/index.jelly @@ -0,0 +1,3 @@ +
              + Demonstration of UI controls available in Jenkins based on Stapler, Jelly, etc. +
              From 5894e301abcb1fe434cee9b7385af3ace11d1cb6 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 22 May 2013 09:54:08 -0400 Subject: [PATCH 116/233] Try harder to display some kind of description for each installed plugin. --- .../hudson/PluginManager/installed.jelly | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/core/src/main/resources/hudson/PluginManager/installed.jelly b/core/src/main/resources/hudson/PluginManager/installed.jelly index bba93b5360..7d5d239f42 100644 --- a/core/src/main/resources/hudson/PluginManager/installed.jelly +++ b/core/src/main/resources/hudson/PluginManager/installed.jelly @@ -63,9 +63,22 @@ THE SOFTWARE.
              - - - + + + + + + + + + + + ${description} + + + ${%No description available.} + +
              From cd3efb21db226037be35fa9b74be84d039140d2f Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 22 May 2013 10:28:00 -0400 Subject: [PATCH 117/233] Avoid gratuitous logging at INFO. --- core/src/main/java/hudson/search/Search.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/main/java/hudson/search/Search.java b/core/src/main/java/hudson/search/Search.java index 0bece56757..7d5f69122f 100644 --- a/core/src/main/java/hudson/search/Search.java +++ b/core/src/main/java/hudson/search/Search.java @@ -343,7 +343,7 @@ public class Search { m.find(index,token,items); for (SearchItem si : items) { paths[w].add(new SuggestedItem(si)); - LOGGER.info("found search item:" + si.getSearchName()); + LOGGER.fine("found search item:" + si.getSearchName()); } w++; } From 63ecb8269aaa8e03fdb46407b70adf6522548b6d Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 22 May 2013 10:30:18 -0400 Subject: [PATCH 118/233] Use message formats when logging. --- core/src/main/java/hudson/search/Search.java | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/core/src/main/java/hudson/search/Search.java b/core/src/main/java/hudson/search/Search.java index 7d5f69122f..c6899a7cdf 100644 --- a/core/src/main/java/hudson/search/Search.java +++ b/core/src/main/java/hudson/search/Search.java @@ -332,9 +332,7 @@ public class Search { List items = new ArrayList(); // items found in 1 step - if(LOGGER.isLoggable(Level.FINE)) { - LOGGER.fine("tokens="+tokens.toString()); - } + LOGGER.log(Level.FINE, "tokens={0}", tokens); // first token int w=1; // width of token @@ -343,7 +341,7 @@ public class Search { m.find(index,token,items); for (SearchItem si : items) { paths[w].add(new SuggestedItem(si)); - LOGGER.fine("found search item:" + si.getSearchName()); + LOGGER.log(Level.FINE, "found search item: {0}", si.getSearchName()); } w++; } From 41edc5867ba194fdb06b2e2ffa6b6addfaa99986 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 22 May 2013 17:20:43 -0400 Subject: [PATCH 119/233] [JENKINS-16301] Verifying current load/save implementation can round-trip fingerprints. --- .../main/java/hudson/model/Fingerprint.java | 10 +++-- .../java/hudson/model/FingerprintTest.java | 45 +++++++++++++++++++ 2 files changed, 52 insertions(+), 3 deletions(-) diff --git a/core/src/main/java/hudson/model/Fingerprint.java b/core/src/main/java/hudson/model/Fingerprint.java index 075fcf9533..7dac1ed6a5 100644 --- a/core/src/main/java/hudson/model/Fingerprint.java +++ b/core/src/main/java/hudson/model/Fingerprint.java @@ -578,7 +578,7 @@ public class Fingerprint implements ModelObject, Saveable { */ private final Hashtable usages = new Hashtable(); - private PersistedList facets = new PersistedList(this); + PersistedList facets = new PersistedList(this); /** * Lazily computed immutable {@link FingerprintFacet}s created from {@link TransientFingerprintFacetFactory}. @@ -712,7 +712,12 @@ public class Fingerprint implements ModelObject, Saveable { * Records that a build of a job has used this file. */ public synchronized void add(String jobFullName, int n) throws IOException { - synchronized(usages) { + addWithoutSaving(jobFullName, n); + save(); + } + + void addWithoutSaving(String jobFullName, int n) { + synchronized(usages) { // XXX why not synchronized (this) like some, though not all, other accesses? RangeSet r = usages.get(jobFullName); if(r==null) { r = new RangeSet(); @@ -720,7 +725,6 @@ public class Fingerprint implements ModelObject, Saveable { } r.add(n); } - save(); } /** diff --git a/core/src/test/java/hudson/model/FingerprintTest.java b/core/src/test/java/hudson/model/FingerprintTest.java index eaa01473d3..1167745c73 100644 --- a/core/src/test/java/hudson/model/FingerprintTest.java +++ b/core/src/test/java/hudson/model/FingerprintTest.java @@ -23,15 +23,21 @@ */ package hudson.model; +import hudson.Util; import hudson.model.Fingerprint.RangeSet; import java.io.File; +import jenkins.model.FingerprintFacet; import static org.junit.Assert.*; +import org.junit.Rule; import org.junit.Test; +import org.junit.rules.TemporaryFolder; /** * @author Kohsuke Kawaguchi */ public class FingerprintTest { + + @Rule public TemporaryFolder tmp = new TemporaryFolder(); @Test public void rangeSet() { RangeSet rs = new RangeSet(); @@ -128,4 +134,43 @@ public class FingerprintTest { Fingerprint.load(new File(FingerprintTest.class.getResource("fingerprint.xml").toURI())).toString()); } + @Test public void roundTrip() throws Exception { + Fingerprint f = new Fingerprint(new Fingerprint.BuildPtr("foo", 13), "stuff.jar", SOME_MD5); + f.addWithoutSaving("some", 1); + f.addWithoutSaving("some", 2); + f.addWithoutSaving("some", 3); + f.addWithoutSaving("some", 10); + f.addWithoutSaving("other", 6); + File xml = tmp.newFile(); + f.save(xml); + Fingerprint f2 = Fingerprint.load(xml); + assertEquals(f.toString(), f2.toString()); + f.facets.setOwner(Saveable.NOOP); + f.facets.add(new TestFacet(f, 123, "val")); + f.save(xml); + //System.out.println(FileUtils.readFileToString(xml)); + f2 = Fingerprint.load(xml); + assertEquals(f.toString(), f2.toString()); + assertEquals(1, f2.facets.size()); + TestFacet facet = (TestFacet) f2.facets.get(0); + assertEquals(f2, facet.getFingerprint()); + } + private static byte[] toByteArray(String md5sum) { + byte[] data = new byte[16]; + for( int i=0; i Date: Wed, 22 May 2013 17:27:52 -0400 Subject: [PATCH 120/233] [FIXED JENKINS-17681] Use builds\last{Stable,Successful}Build on Windows for permalinks. --- core/src/main/java/hudson/model/AbstractBuild.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/core/src/main/java/hudson/model/AbstractBuild.java b/core/src/main/java/hudson/model/AbstractBuild.java index e4ff4b86c1..b553723bf3 100644 --- a/core/src/main/java/hudson/model/AbstractBuild.java +++ b/core/src/main/java/hudson/model/AbstractBuild.java @@ -487,9 +487,9 @@ public abstract class AbstractBuild

              ,R extends Abs private void createSymlink(TaskListener listener, String name, Permalink target) throws InterruptedException { String targetDir; if (getProject().getBuildDir().equals(new File(getProject().getRootDir(), "builds"))) { - targetDir = "builds/" + target.getId(); + targetDir = "builds" + File.separator + target.getId(); } else { - targetDir = getProject().getBuildDir()+"/"+target.getId(); + targetDir = getProject().getBuildDir() + File.separator + target.getId(); } Util.createSymlink(getProject().getRootDir(), targetDir, name, listener); } From b1415bda59e1020c433a63ff1830a3012eb04428 Mon Sep 17 00:00:00 2001 From: gcummings Date: Tue, 5 Mar 2013 15:05:00 +0000 Subject: [PATCH 121/233] JENKINS-7280 - Allow filtering of the Run Paramters List - All, Completed, Successful & Stable using Enum --- .../hudson/model/RunParameterDefinition.java | 85 +++++++- .../java/hudson/model/RunParameterValue.java | 5 +- core/src/main/java/hudson/util/RunList.java | 15 +- .../model/RunParameterDefinition/config.jelly | 8 + .../model/RunParameterDefinition/index.jelly | 2 +- .../java/hudson/model/ParametersTest.java | 2 +- .../model/RunParameterDefinitionTest.java | 203 +++++++++++++++++- .../webapp/help/parameter/run-filter.html | 9 + .../webapp/help/parameter/run-project.html | 1 + 9 files changed, 318 insertions(+), 12 deletions(-) create mode 100755 war/src/main/webapp/help/parameter/run-filter.html diff --git a/core/src/main/java/hudson/model/RunParameterDefinition.java b/core/src/main/java/hudson/model/RunParameterDefinition.java index 04d074f01e..107263f4c9 100644 --- a/core/src/main/java/hudson/model/RunParameterDefinition.java +++ b/core/src/main/java/hudson/model/RunParameterDefinition.java @@ -1,7 +1,7 @@ /* * The MIT License * - * Copyright (c) 2004-2009, Sun Microsystems, Inc., Kohsuke Kawaguchi, Tom Huybrechts + * Copyright (c) 2004-2009, Sun Microsystems, Inc., Kohsuke Kawaguchi, Tom Huybrechts, Geoff Cummings * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal @@ -30,31 +30,63 @@ import org.kohsuke.stapler.DataBoundConstructor; import org.kohsuke.stapler.StaplerRequest; import org.kohsuke.stapler.export.Exported; import hudson.Extension; +import hudson.util.EnumConverter; +import hudson.util.RunList; +import org.kohsuke.stapler.Stapler; import org.kohsuke.stapler.QueryParameter; public class RunParameterDefinition extends SimpleParameterDefinition { + /** + * Constants that control how Run Parameter is filtered + */ + public enum RunParameterFilter { + ALL, + STABLE, + SUCCESSFUL, + COMPLETED; + + public String getName() { + return name(); + } + + static { + Stapler.CONVERT_UTILS.register(new EnumConverter(), RunParameterFilter.class); + } + } + private final String projectName; private final String runId; + private final RunParameterFilter filter; @DataBoundConstructor - public RunParameterDefinition(String name, String projectName, String description) { + public RunParameterDefinition(String name, String projectName, String description, RunParameterFilter filter) { super(name, description); this.projectName = projectName; this.runId = null; + this.filter = filter; } - private RunParameterDefinition(String name, String projectName, String runId, String description) { + /** + * @deprecated as of 1.517 + */ + public RunParameterDefinition(String name, String projectName, String description) { + // delegate to updated constructor with additional RunParameterFilter parameter defaulted to ALL. + this(name, projectName, description, RunParameterFilter.ALL); + } + + private RunParameterDefinition(String name, String projectName, String runId, String description, RunParameterFilter filter) { super(name, description); this.projectName = projectName; this.runId = runId; + this.filter = filter; } @Override public ParameterDefinition copyWithDefaultValue(ParameterValue defaultValue) { if (defaultValue instanceof RunParameterValue) { RunParameterValue value = (RunParameterValue) defaultValue; - return new RunParameterDefinition(getName(), value.getRunId(), getDescription()); + return new RunParameterDefinition(getName(), value.getRunId(), getDescription(), getFilter()); } else { return this; } @@ -69,6 +101,32 @@ public class RunParameterDefinition extends SimpleParameterDefinition { return Jenkins.getInstance().getItemByFullName(projectName, Job.class); } + /** + * @return The current filter value, if filter is null, returns ALL + */ + public RunParameterFilter getFilter() { + // if filter is null, default to RunParameterFilter.ALL + return (null == filter) ? RunParameterFilter.ALL : filter; + } + + /** + * @since 1.517 + * @return Returns a list of builds, filtered based on the filter value. + */ + public RunList getBuilds() { + // use getFilter() method so we dont have to worry about null filter value. + switch (getFilter()) { + case COMPLETED: + return getProject().getBuilds().overThresholdOnly(Result.ABORTED); + case SUCCESSFUL: + return getProject().getBuilds().overThresholdOnly(Result.UNSTABLE); + case STABLE : + return getProject().getBuilds().overThresholdOnly(Result.SUCCESS); + default: + return getProject().getBuilds(); + } + } + @Extension public static class DescriptorImpl extends ParameterDescriptor { @Override @@ -98,7 +156,24 @@ public class RunParameterDefinition extends SimpleParameterDefinition { return createValue(runId); } - Run lastBuild = getProject().getLastBuild(); + Run lastBuild = null; + + // use getFilter() so we dont have to worry about null filter value. + switch (getFilter()) { + case COMPLETED: + lastBuild = getProject().getLastCompletedBuild(); + break; + case SUCCESSFUL: + lastBuild = getProject().getLastSuccessfulBuild(); + break; + case STABLE : + lastBuild = getProject().getLastStableBuild(); + break; + default: + lastBuild = getProject().getLastBuild(); + break; + } + if (lastBuild != null) { return createValue(lastBuild.getExternalizableId()); } else { diff --git a/core/src/main/java/hudson/model/RunParameterValue.java b/core/src/main/java/hudson/model/RunParameterValue.java index 3ee6072cad..6368a94277 100644 --- a/core/src/main/java/hudson/model/RunParameterValue.java +++ b/core/src/main/java/hudson/model/RunParameterValue.java @@ -1,7 +1,7 @@ /* * The MIT License * - * Copyright (c) 2004-2009, Sun Microsystems, Inc., Kohsuke Kawaguchi, Tom Huybrechts + * Copyright (c) 2004-2009, Sun Microsystems, Inc., Kohsuke Kawaguchi, Tom Huybrechts, Geoff Cummings * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal @@ -82,6 +82,9 @@ public class RunParameterValue extends ParameterValue { env.put(name + "_NAME", run.getDisplayName()); // since 1.504 + String buildResult = (null == run.getResult()) ? "UNKNOWN" : run.getResult().toString(); + env.put(name + "_RESULT", buildResult); // since 1.517 + env.put(name.toUpperCase(Locale.ENGLISH),value); // backward compatibility pre 1.345 } diff --git a/core/src/main/java/hudson/util/RunList.java b/core/src/main/java/hudson/util/RunList.java index 25f7deadd3..0fc740a3f1 100644 --- a/core/src/main/java/hudson/util/RunList.java +++ b/core/src/main/java/hudson/util/RunList.java @@ -1,7 +1,7 @@ /* * The MIT License * - * Copyright (c) 2004-2009, Sun Microsystems, Inc., Kohsuke Kawaguchi + * Copyright (c) 2004-2009, Sun Microsystems, Inc., Kohsuke Kawaguchi, Geoff Cummings * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal @@ -240,6 +240,19 @@ public class RunList extends AbstractList { }); } + /** + * Filter the list to builds >= threshold. + * + * @since 1.516 + */ + public RunList overThresholdOnly(final Result threshold) { + return filter(new Predicate() { + public boolean apply(R r) { + return (r.getResult() != null && r.getResult().isBetterOrEqualTo(threshold)); + } + }); + } + /** * Filter the list to builds on a single node only */ diff --git a/core/src/main/resources/hudson/model/RunParameterDefinition/config.jelly b/core/src/main/resources/hudson/model/RunParameterDefinition/config.jelly index 007c8e0bdc..16aeae2d46 100755 --- a/core/src/main/resources/hudson/model/RunParameterDefinition/config.jelly +++ b/core/src/main/resources/hudson/model/RunParameterDefinition/config.jelly @@ -35,4 +35,12 @@ THE SOFTWARE. + + + \ No newline at end of file diff --git a/core/src/main/resources/hudson/model/RunParameterDefinition/index.jelly b/core/src/main/resources/hudson/model/RunParameterDefinition/index.jelly index 486ab16d62..600f6b4f86 100755 --- a/core/src/main/resources/hudson/model/RunParameterDefinition/index.jelly +++ b/core/src/main/resources/hudson/model/RunParameterDefinition/index.jelly @@ -30,7 +30,7 @@ THE SOFTWARE.

              diff --git a/test/src/test/java/hudson/model/ParametersTest.java b/test/src/test/java/hudson/model/ParametersTest.java index 9e32f79653..b5aa636c6e 100755 --- a/test/src/test/java/hudson/model/ParametersTest.java +++ b/test/src/test/java/hudson/model/ParametersTest.java @@ -24,7 +24,7 @@ public class ParametersTest extends HudsonTestCase { new StringParameterDefinition("string", "defaultValue", "string description"), new BooleanParameterDefinition("boolean", true, "boolean description"), new ChoiceParameterDefinition("choice", "Choice 1\nChoice 2", "choice description"), - new RunParameterDefinition("run", otherProject.getName(), "run description")); + new RunParameterDefinition("run", otherProject.getName(), "run description", null)); project.addProperty(pdp); CaptureEnvironmentBuilder builder = new CaptureEnvironmentBuilder(); project.getBuildersList().add(builder); diff --git a/test/src/test/java/hudson/model/RunParameterDefinitionTest.java b/test/src/test/java/hudson/model/RunParameterDefinitionTest.java index 7d0da8964c..1f0e909507 100644 --- a/test/src/test/java/hudson/model/RunParameterDefinitionTest.java +++ b/test/src/test/java/hudson/model/RunParameterDefinitionTest.java @@ -1,7 +1,7 @@ /* * The MIT License * - * Copyright 2013 Jesse Glick. + * Copyright 2013 Jesse Glick, Geoff Cummings * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal @@ -26,6 +26,16 @@ package hudson.model; import hudson.EnvVars; import static org.junit.Assert.*; +import hudson.Launcher; +import hudson.model.RunParameterDefinition.RunParameterFilter; +import hudson.tasks.BuildStepMonitor; +import hudson.tasks.Publisher; +import hudson.util.LogTaskListener; + +import java.util.Collections; +import java.util.logging.Level; +import java.util.logging.Logger; + import org.junit.Rule; import org.junit.Test; import org.jvnet.hudson.test.Bug; @@ -34,7 +44,10 @@ import org.jvnet.hudson.test.MockFolder; public class RunParameterDefinitionTest { - @Rule public JenkinsRule j = new JenkinsRule(); + private static final Logger LOGGER = Logger.getLogger(Run.class.getName()); + + @Rule + public JenkinsRule j = new JenkinsRule(); @Bug(16462) @Test public void inFolders() throws Exception { @@ -47,7 +60,7 @@ public class RunParameterDefinitionTest { String id = build2.getExternalizableId(); assertEquals("dir/sub dir/some project#2", id); assertEquals(build2, Run.fromExternalizableId(id)); - RunParameterDefinition def = new RunParameterDefinition("build", "dir/sub dir/some project", "my build"); + RunParameterDefinition def = new RunParameterDefinition("build", "dir/sub dir/some project", "my build", null); assertEquals("dir/sub dir/some project", def.getProjectName()); assertEquals(p, def.getProject()); EnvVars env = new EnvVars(); @@ -65,4 +78,188 @@ public class RunParameterDefinitionTest { assertEquals("2", env.get("build_NUMBER")); } + @Test + public void testNULLFilter() throws Exception { + + FreeStyleProject project = j.createFreeStyleProject("project"); + FreeStyleBuild successfulBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.UNSTABLE))); + FreeStyleBuild unstableBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.FAILURE))); + FreeStyleBuild failedBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.NOT_BUILT))); + FreeStyleBuild notBuiltBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.ABORTED))); + FreeStyleBuild abortedBuild = project.scheduleBuild2(0).get(); + + FreeStyleProject paramProject = j.createFreeStyleProject("paramProject"); + ParametersDefinitionProperty pdp = + new ParametersDefinitionProperty(new RunParameterDefinition("RUN", + project.getName(), + "run description", + null)); + paramProject.addProperty(pdp); + + FreeStyleBuild build = paramProject.scheduleBuild2(0).get(); + assertEquals(Integer.toString(project.getLastBuild().getNumber()), + build.getEnvironment(new LogTaskListener(LOGGER, Level.INFO)).get("RUN_NUMBER")); + } + + + @Test + public void testALLFilter() throws Exception { + + FreeStyleProject project = j.createFreeStyleProject("project"); + FreeStyleBuild successfulBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.UNSTABLE))); + FreeStyleBuild unstableBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.FAILURE))); + FreeStyleBuild failedBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.NOT_BUILT))); + FreeStyleBuild notBuiltBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.ABORTED))); + FreeStyleBuild abortedBuild = project.scheduleBuild2(0).get(); + + FreeStyleProject paramProject = j.createFreeStyleProject("paramProject"); + ParametersDefinitionProperty pdp = + new ParametersDefinitionProperty(new RunParameterDefinition("RUN", + project.getName(), + "run description", + RunParameterFilter.ALL)); + paramProject.addProperty(pdp); + + FreeStyleBuild build = paramProject.scheduleBuild2(0).get(); + assertEquals(Integer.toString(project.getLastBuild().getNumber()), + build.getEnvironment(new LogTaskListener(LOGGER, Level.INFO)).get("RUN_NUMBER")); + } + + @Test + public void testCOMPLETEDFilter() throws Exception { + + FreeStyleProject project = j.createFreeStyleProject("project"); + FreeStyleBuild successfulBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.UNSTABLE))); + FreeStyleBuild unstableBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.FAILURE))); + FreeStyleBuild failedBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.NOT_BUILT))); + FreeStyleBuild notBuiltBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.ABORTED))); + FreeStyleBuild abortedBuild = project.scheduleBuild2(0).get(); + + FreeStyleProject paramProject = j.createFreeStyleProject("paramProject"); + ParametersDefinitionProperty pdp = + new ParametersDefinitionProperty(new RunParameterDefinition("RUN", + project.getName(), + "run description", + RunParameterFilter.COMPLETED)); + paramProject.addProperty(pdp); + + FreeStyleBuild build = paramProject.scheduleBuild2(0).get(); + assertEquals(Integer.toString(abortedBuild.getNumber()), + build.getEnvironment(new LogTaskListener(LOGGER, Level.INFO)).get("RUN_NUMBER")); + } + + @Test + public void testSUCCESSFULFilter() throws Exception { + + FreeStyleProject project = j.createFreeStyleProject("project"); + FreeStyleBuild successfulBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.UNSTABLE))); + FreeStyleBuild unstableBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.FAILURE))); + FreeStyleBuild failedBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.NOT_BUILT))); + FreeStyleBuild notBuiltBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.ABORTED))); + FreeStyleBuild abortedBuild = project.scheduleBuild2(0).get(); + + FreeStyleProject paramProject = j.createFreeStyleProject("paramProject"); + ParametersDefinitionProperty pdp = + new ParametersDefinitionProperty(new RunParameterDefinition("RUN", + project.getName(), + "run description", + RunParameterFilter.SUCCESSFUL)); + paramProject.addProperty(pdp); + + FreeStyleBuild build = paramProject.scheduleBuild2(0).get(); + assertEquals(Integer.toString(unstableBuild.getNumber()), + build.getEnvironment(new LogTaskListener(LOGGER, Level.INFO)).get("RUN_NUMBER")); + } + + + @Test + public void testSTABLEFilter() throws Exception { + + FreeStyleProject project = j.createFreeStyleProject("project"); + FreeStyleBuild successfulBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.UNSTABLE))); + FreeStyleBuild unstableBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.FAILURE))); + FreeStyleBuild failedBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.NOT_BUILT))); + FreeStyleBuild notBuiltBuild = project.scheduleBuild2(0).get(); + + project.getPublishersList().replaceBy(Collections.singleton(new ResultPublisher(Result.ABORTED))); + FreeStyleBuild abortedBuild = project.scheduleBuild2(0).get(); + + FreeStyleProject paramProject = j.createFreeStyleProject("paramProject"); + ParametersDefinitionProperty pdp = + new ParametersDefinitionProperty(new RunParameterDefinition("RUN", + project.getName(), + "run description", + RunParameterFilter.STABLE)); + paramProject.addProperty(pdp); + + FreeStyleBuild build = paramProject.scheduleBuild2(0).get(); + assertEquals(Integer.toString(successfulBuild.getNumber()), + build.getEnvironment(new LogTaskListener(LOGGER, Level.INFO)).get("RUN_NUMBER")); + } + + + static class ResultPublisher extends Publisher { + + private Result result = Result.FAILURE; + + public ResultPublisher(Result result) { + this.result = result; + } + + public @Override + boolean perform(AbstractBuild build, Launcher launcher, BuildListener listener) { + build.setResult(result); + return true; + } + + public BuildStepMonitor getRequiredMonitorService() { + return BuildStepMonitor.NONE; + } + + public Descriptor getDescriptor() { + return new Descriptor(ResultPublisher.class) { + public String getDisplayName() { + return "ResultPublisher"; + } + }; + } + } } diff --git a/war/src/main/webapp/help/parameter/run-filter.html b/war/src/main/webapp/help/parameter/run-filter.html new file mode 100755 index 0000000000..98b3bf9ac8 --- /dev/null +++ b/war/src/main/webapp/help/parameter/run-filter.html @@ -0,0 +1,9 @@ +
              +Filter the list of builds which are included in the drop-down list. +
              +'All Builds' - List all builds including in-progress builds.
              +'Completed Builds Only' - List all completed builds.
              +'Successful Builds Only' - List all Successful builds (Stable and Unstable)
              +'Stable Builds Only' - List all Stable builds.
              +
              +
              diff --git a/war/src/main/webapp/help/parameter/run-project.html b/war/src/main/webapp/help/parameter/run-project.html index 36ab460547..239784ea32 100755 --- a/war/src/main/webapp/help/parameter/run-project.html +++ b/war/src/main/webapp/help/parameter/run-project.html @@ -6,5 +6,6 @@ PARAMETER_NAME=<jenkins_url>/job/<job_name>/<run_number PARAMETER_NAME_JOBNAME=<job_name> PARAMETER_NAME_NUMBER=<run_number> PARAMETER_NAME_NAME=<display_name> +PARAMETER_NAME_RESULT=<run_result>
              \ No newline at end of file From f49e3a1953c1bddb5c9bf8d5fb93df8da5f59a0e Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 23 May 2013 10:15:47 -0400 Subject: [PATCH 122/233] [FIXED JENKINS-18025] Noting PR #763. --- changelog.html | 3 +++ 1 file changed, 3 insertions(+) diff --git a/changelog.html b/changelog.html index 5629717a90..091ba441e3 100644 --- a/changelog.html +++ b/changelog.html @@ -58,6 +58,9 @@ Upcoming changes
            • Enable word breaking in potentially long strings like job names. (issue 17030) +
            • + “Recurse in subfolders” option for list views produced exceptions when used with native Maven projects. + (issue 18025)
            From 334d3218ebccf7d397e8e542303bc81dbe67ca51 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 23 May 2013 10:20:19 -0400 Subject: [PATCH 123/233] [JENKINS-17681] Noting. --- changelog.html | 3 +++ 1 file changed, 3 insertions(+) diff --git a/changelog.html b/changelog.html index 091ba441e3..13aba769ff 100644 --- a/changelog.html +++ b/changelog.html @@ -61,6 +61,9 @@ Upcoming changes
          • “Recurse in subfolders” option for list views produced exceptions when used with native Maven projects. (issue 18025) +
          • + Using proper directory separator character for permalinks on Windows. + (issue 17681)
          From 53cbf595ed487f2239ea63b2f8ae7d2f48ad47f5 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 23 May 2013 11:05:40 -0400 Subject: [PATCH 124/233] [JENKINS-7280] Touch-ups. --- changelog.html | 3 +++ .../src/main/java/hudson/model/RunParameterDefinition.java | 7 ++++++- core/src/main/java/hudson/util/RunList.java | 4 ++-- .../test/java/hudson/model/RunParameterDefinitionTest.java | 2 +- 4 files changed, 12 insertions(+), 4 deletions(-) diff --git a/changelog.html b/changelog.html index 13aba769ff..4620974138 100644 --- a/changelog.html +++ b/changelog.html @@ -58,6 +58,9 @@ Upcoming changes
        • Enable word breaking in potentially long strings like job names. (issue 17030) +
        • + Allow filtering of the Run parameter build list by result. + (issue 7280)
        • “Recurse in subfolders” option for list views produced exceptions when used with native Maven projects. (issue 18025) diff --git a/core/src/main/java/hudson/model/RunParameterDefinition.java b/core/src/main/java/hudson/model/RunParameterDefinition.java index 107263f4c9..bacef92a08 100644 --- a/core/src/main/java/hudson/model/RunParameterDefinition.java +++ b/core/src/main/java/hudson/model/RunParameterDefinition.java @@ -38,7 +38,8 @@ import org.kohsuke.stapler.QueryParameter; public class RunParameterDefinition extends SimpleParameterDefinition { /** - * Constants that control how Run Parameter is filtered + * Constants that control how Run Parameter is filtered. + * @since 1.517 */ public enum RunParameterFilter { ALL, @@ -59,6 +60,9 @@ public class RunParameterDefinition extends SimpleParameterDefinition { private final String runId; private final RunParameterFilter filter; + /** + * @since 1.517 + */ @DataBoundConstructor public RunParameterDefinition(String name, String projectName, String description, RunParameterFilter filter) { super(name, description); @@ -103,6 +107,7 @@ public class RunParameterDefinition extends SimpleParameterDefinition { /** * @return The current filter value, if filter is null, returns ALL + * @since 1.517 */ public RunParameterFilter getFilter() { // if filter is null, default to RunParameterFilter.ALL diff --git a/core/src/main/java/hudson/util/RunList.java b/core/src/main/java/hudson/util/RunList.java index 0fc740a3f1..d80397bc93 100644 --- a/core/src/main/java/hudson/util/RunList.java +++ b/core/src/main/java/hudson/util/RunList.java @@ -241,9 +241,9 @@ public class RunList extends AbstractList { } /** - * Filter the list to builds >= threshold. + * Filter the list to builds above threshold. * - * @since 1.516 + * @since 1.517 */ public RunList overThresholdOnly(final Result threshold) { return filter(new Predicate() { diff --git a/test/src/test/java/hudson/model/RunParameterDefinitionTest.java b/test/src/test/java/hudson/model/RunParameterDefinitionTest.java index 1f0e909507..f0b7efe86a 100644 --- a/test/src/test/java/hudson/model/RunParameterDefinitionTest.java +++ b/test/src/test/java/hudson/model/RunParameterDefinitionTest.java @@ -238,7 +238,7 @@ public class RunParameterDefinitionTest { static class ResultPublisher extends Publisher { - private Result result = Result.FAILURE; + private final Result result; public ResultPublisher(Result result) { this.result = result; From 186c425d559d098637dc5c1f6cba5b8fc5da248a Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 23 May 2013 12:56:36 -0400 Subject: [PATCH 125/233] @since --- .../src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java | 1 + 1 file changed, 1 insertion(+) diff --git a/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java b/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java index 55fc64950c..81dc42141d 100644 --- a/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java +++ b/core/src/main/java/jenkins/model/lazy/AbstractLazyLoadRunMap.java @@ -215,6 +215,7 @@ public abstract class AbstractLazyLoadRunMap extends AbstractMap i * * This is a bit more sophisticated version of forcing GC. * Primarily for debugging and testing lazy loading behaviour. + * @since 1.507 */ public void purgeCache() { index = new Index(); From ef926d8a8f79f12af18b14878cb9302a37af1d20 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 23 May 2013 13:40:48 -0400 Subject: [PATCH 126/233] Javadoc and @since. --- core/src/main/java/hudson/util/RunList.java | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/core/src/main/java/hudson/util/RunList.java b/core/src/main/java/hudson/util/RunList.java index d80397bc93..4e1ea03a5a 100644 --- a/core/src/main/java/hudson/util/RunList.java +++ b/core/src/main/java/hudson/util/RunList.java @@ -221,6 +221,12 @@ public class RunList extends AbstractList { return this; } + /** + * Return only the most recent builds. + * @param n a count + * @return the n most recent builds + * @since 1.507 + */ public RunList limit(final int n) { return limit(new CountingPredicate() { public boolean apply(int index, R input) { From 1551ad6e4683f0b602e4886f2e97f0daf09151bb Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 23 May 2013 13:55:54 -0400 Subject: [PATCH 127/233] Warning about mutable design, not apparent from API signature. --- core/src/main/java/hudson/util/RunList.java | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/core/src/main/java/hudson/util/RunList.java b/core/src/main/java/hudson/util/RunList.java index 4e1ea03a5a..c86b0b0da5 100644 --- a/core/src/main/java/hudson/util/RunList.java +++ b/core/src/main/java/hudson/util/RunList.java @@ -223,6 +223,7 @@ public class RunList extends AbstractList { /** * Return only the most recent builds. + * Warning: this method mutates the original list and then returns it. * @param n a count * @return the n most recent builds * @since 1.507 @@ -237,6 +238,7 @@ public class RunList extends AbstractList { /** * Filter the list to non-successful builds only. + * Warning: this method mutates the original list and then returns it. */ public RunList failureOnly() { return filter(new Predicate() { @@ -248,7 +250,7 @@ public class RunList extends AbstractList { /** * Filter the list to builds above threshold. - * + * Warning: this method mutates the original list and then returns it. * @since 1.517 */ public RunList overThresholdOnly(final Result threshold) { @@ -261,6 +263,7 @@ public class RunList extends AbstractList { /** * Filter the list to builds on a single node only + * Warning: this method mutates the original list and then returns it. */ public RunList node(final Node node) { return filter(new Predicate() { @@ -272,6 +275,7 @@ public class RunList extends AbstractList { /** * Filter the list to regression builds only. + * Warning: this method mutates the original list and then returns it. */ public RunList regressionOnly() { return filter(new Predicate() { @@ -285,6 +289,7 @@ public class RunList extends AbstractList { * Filter the list by timestamp. * * {@code s<=;e}. + * Warning: this method mutates the original list and then returns it. */ public RunList byTimestamp(final long start, final long end) { return @@ -303,6 +308,7 @@ public class RunList extends AbstractList { * Reduce the size of the list by only leaving relatively new ones. * This also removes on-going builds, as RSS cannot be used to publish information * if it changes. + * Warning: this method mutates the original list and then returns it. */ public RunList newBuilds() { GregorianCalendar cal = new GregorianCalendar(); From 328b9c8d9ddb85b1aafcce78e7873e81a6bff10f Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 23 May 2013 14:40:10 -0400 Subject: [PATCH 128/233] toString --- .../java/jenkins/model/lazy/BuildReferenceMapAdapter.java | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/core/src/main/java/jenkins/model/lazy/BuildReferenceMapAdapter.java b/core/src/main/java/jenkins/model/lazy/BuildReferenceMapAdapter.java index f8903e7645..9a92c10c32 100644 --- a/core/src/main/java/jenkins/model/lazy/BuildReferenceMapAdapter.java +++ b/core/src/main/java/jenkins/model/lazy/BuildReferenceMapAdapter.java @@ -10,6 +10,7 @@ import java.util.ArrayList; import java.util.Collection; import java.util.Comparator; import java.util.Iterator; +import java.util.LinkedHashMap; import java.util.List; import java.util.Map; import java.util.Set; @@ -125,7 +126,7 @@ class BuildReferenceMapAdapter implements SortedMap { @Override public boolean equals(Object o) { - return core.equals(o); + return core.equals(o); // XXX this is wrong } @Override @@ -133,6 +134,10 @@ class BuildReferenceMapAdapter implements SortedMap { return core.hashCode(); } + @Override public String toString() { + return new LinkedHashMap(this).toString(); + } + private class CollectionAdapter implements Collection { private final Collection> core; From 03ca63c62c1f3e20f405b655bbc610ed21931a86 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Thu, 23 May 2013 15:07:54 -0400 Subject: [PATCH 129/233] Lazy-loading utility test class designed for fix of JENKINS-15858. --- .../org/jvnet/hudson/test/RunLoadCounter.java | 150 ++++++++++++++++++ 1 file changed, 150 insertions(+) create mode 100644 test/src/main/java/org/jvnet/hudson/test/RunLoadCounter.java diff --git a/test/src/main/java/org/jvnet/hudson/test/RunLoadCounter.java b/test/src/main/java/org/jvnet/hudson/test/RunLoadCounter.java new file mode 100644 index 0000000000..84a0d18b3d --- /dev/null +++ b/test/src/main/java/org/jvnet/hudson/test/RunLoadCounter.java @@ -0,0 +1,150 @@ +/* + * The MIT License + * + * Copyright 2013 Jesse Glick. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +package org.jvnet.hudson.test; + +import hudson.Launcher; +import hudson.model.AbstractBuild; +import hudson.model.AbstractProject; +import hudson.model.BuildListener; +import hudson.model.Run; +import hudson.model.RunAction; +import hudson.tasks.BuildStepMonitor; +import hudson.tasks.Notifier; +import java.io.IOException; +import java.util.concurrent.Callable; +import java.util.concurrent.atomic.AtomicInteger; +import org.kohsuke.accmod.Restricted; +import org.kohsuke.accmod.restrictions.NoExternalUse; + +/** + * Utility to determine when a build record is loaded. + * @since 1.517 + */ +@SuppressWarnings({"unchecked", "rawtypes"}) // API design mistakes +public final class RunLoadCounter { + + private static final ThreadLocal currProject = new ThreadLocal(); + private static final ThreadLocal currCount = new ThreadLocal(); + + /** + * Prepares a new project to be measured. + * Call this before starting builds. + * @param project a project of any kind + * @throws IOException if preparations fail + */ + public static void prepare(AbstractProject project) throws IOException { + project.getPublishersList().add(new MarkerAdder()); + } + + /** + * Counts how many build records are loaded as a result of some task. + * @param project a project on which {@link #prepare} was called prior to creating builds + * @param thunk a task which is expected to load some build records + * @return how many build records were actually {@linkplain Run#onLoad loaded} as a result + */ + public static int countLoads(AbstractProject project, Runnable thunk) { + project._getRuns().purgeCache(); + currProject.set(project.getFullName()); + currCount.set(new AtomicInteger()); + thunk.run(); + return currCount.get().get(); + } + + /** + * Asserts that at most a certain number of build records are loaded as a result of some task. + * @param project a project on which {@link #prepare} was called prior to creating builds + * @param max the maximum number of build records we expect to load + * @param thunk a task which is expected to load some build records + * @return the result of the task, if any + * @throws Exception if the task failed + * @throws AssertionError if one more than max build record is loaded + * @param the return value type + */ + public static T assertMaxLoads(AbstractProject project, int max, Callable thunk) throws Exception { + project._getRuns().purgeCache(); + currProject.set(project.getFullName()); + currCount.set(new AtomicInteger(-(max + 1))); + return thunk.call(); + } + + private RunLoadCounter() {} + + /** + * Used internally. + */ + @Restricted(NoExternalUse.class) + public static final class Marker implements RunAction { + + private final String project; + private final int build; + + Marker(String project, int build) { + this.project = project; + this.build = build; + } + + @Override public void onLoad() { + if (project.equals(currProject.get())) { + System.err.println("loaded " + project + " #" + build); + assert currCount.get().incrementAndGet() != 0 : "too many build records loaded from " + project; + } + } + + @Override public void onAttached(Run r) {} + + @Override public void onBuildComplete() {} + + @Override public String getIconFileName() { + return null; + } + + @Override public String getDisplayName() { + return null; + } + + @Override public String getUrlName() { + return null; + } + + } + + /** + * Used internally. + */ + @Restricted(NoExternalUse.class) + public static final class MarkerAdder extends Notifier { + + @Override public boolean perform(AbstractBuild build, Launcher launcher, BuildListener listener) throws InterruptedException, IOException { + build.addAction(new Marker(build.getParent().getFullName(), build.getNumber())); + return true; + } + + @Override public BuildStepMonitor getRequiredMonitorService() { + return BuildStepMonitor.NONE; + } + + } + +} From e8c1133e00e33af8d795c3fd9bc13d3cab2e6b0a Mon Sep 17 00:00:00 2001 From: Damien Finck Date: Thu, 23 May 2013 22:28:18 +0200 Subject: [PATCH 130/233] Convert french translations files to ascii --- .../matrix/MatrixBuild/ajaxMatrix_fr.properties | 2 +- .../matrix/MatrixProject/ajaxMatrix_fr.properties | 2 +- .../resources/hudson/slaves/Messages_fr.properties | 12 ++++++------ .../OfflineCause/LaunchFailed/cause_fr.properties | 2 +- 4 files changed, 9 insertions(+), 9 deletions(-) diff --git a/core/src/main/resources/hudson/matrix/MatrixBuild/ajaxMatrix_fr.properties b/core/src/main/resources/hudson/matrix/MatrixBuild/ajaxMatrix_fr.properties index 51dbd9494b..c69d14d921 100644 --- a/core/src/main/resources/hudson/matrix/MatrixBuild/ajaxMatrix_fr.properties +++ b/core/src/main/resources/hudson/matrix/MatrixBuild/ajaxMatrix_fr.properties @@ -20,4 +20,4 @@ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. -Not\ run=Non lancĂŠ +Not\ run=Non lanc\u00e9 diff --git a/core/src/main/resources/hudson/matrix/MatrixProject/ajaxMatrix_fr.properties b/core/src/main/resources/hudson/matrix/MatrixProject/ajaxMatrix_fr.properties index cedf0e56cb..96b16d1808 100644 --- a/core/src/main/resources/hudson/matrix/MatrixProject/ajaxMatrix_fr.properties +++ b/core/src/main/resources/hudson/matrix/MatrixProject/ajaxMatrix_fr.properties @@ -20,4 +20,4 @@ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. -Not\ configured=Non configurĂŠ +Not\ configured=Non configur\u00e9 diff --git a/core/src/main/resources/hudson/slaves/Messages_fr.properties b/core/src/main/resources/hudson/slaves/Messages_fr.properties index 2014b3d245..bbf3373322 100644 --- a/core/src/main/resources/hudson/slaves/Messages_fr.properties +++ b/core/src/main/resources/hudson/slaves/Messages_fr.properties @@ -21,13 +21,13 @@ # THE SOFTWARE. RetentionStrategy.Always.displayName=Garder cet esclave en ligne autant que possible -RetentionStrategy.Demand.displayName=Mettre cet esclave en ligne Ă  la demande et hors-ligne si inutilisĂŠ -CommandLauncher.displayName=Lancer l''esclave via l''exĂŠcution d''une commande sur le maĂŽtre +RetentionStrategy.Demand.displayName=Mettre cet esclave en ligne \u00e0 la demande et hors-ligne si inutilis\u00e9 +CommandLauncher.displayName=Lancer l''esclave via l''ex\u00e9cution d''une commande sur le ma\u00eetre JNLPLauncher.displayName=Lancer les agents esclaves par JNLP ComputerLauncher.unexpectedError=Erreur inattendue au lancement d''un esclave. Probablement un bug dans Jenkins -ComputerLauncher.abortedLaunch=Lancement de l''esclave annulĂŠ. -CommandLauncher.NoLaunchCommand=Aucune commande de lancement spĂŠcifiĂŠe +ComputerLauncher.abortedLaunch=Lancement de l''esclave annul\u00e9. +CommandLauncher.NoLaunchCommand=Aucune commande de lancement sp\u00e9cifi\u00e9e DumbSlave.displayName=Esclave passif -OfflineCause.LaunchFailed=Ce noeud est dĂŠconnectĂŠ parce que Jenkins n''a pas rĂŠussi Ă  lancer l''agent esclave dessus. -SimpleScheduledRetentionStrategy.displayName=DĂŠconnecte cet esclave selon des horaires +OfflineCause.LaunchFailed=Ce noeud est d\u00e9connect\u00e9 parce que Jenkins n''a pas r\u00e9ussi \u00e0 lancer l''agent esclave dessus. +SimpleScheduledRetentionStrategy.displayName=D\u00e9connecte cet esclave selon des horaires EnvironmentVariablesNodeProperty.displayName=Variables d''environnement diff --git a/core/src/main/resources/hudson/slaves/OfflineCause/LaunchFailed/cause_fr.properties b/core/src/main/resources/hudson/slaves/OfflineCause/LaunchFailed/cause_fr.properties index 6faaa64d97..2069e0631d 100644 --- a/core/src/main/resources/hudson/slaves/OfflineCause/LaunchFailed/cause_fr.properties +++ b/core/src/main/resources/hudson/slaves/OfflineCause/LaunchFailed/cause_fr.properties @@ -20,4 +20,4 @@ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. -See\ log\ for\ more\ details=Voir les logs pour plus de dĂŠtails +See\ log\ for\ more\ details=Voir les logs pour plus de d\u00e9tails From 4d1bafa4fbd60ab545527a2deaf37ef14881aacf Mon Sep 17 00:00:00 2001 From: Damien Finck Date: Fri, 24 May 2013 07:39:12 +0200 Subject: [PATCH 131/233] Added French translation --- .../hudson/AboutJenkins/index_fr.properties | 1 + .../resources/hudson/Messages_fr.properties | 3 +++ .../hudson/model/Messages_fr.properties | 4 ++-- .../model/Jenkins/legend_fr.properties | 22 +++++++---------- .../lib/layout/breadcrumbBar_fr.properties | 24 +++++++++++++++++++ .../resources/lib/layout/layout_fr.properties | 2 -- .../layout/progressiveRendering_fr.properties | 23 ++++++++++++++++++ .../resources/lib/layout/task_fr.properties | 23 ++++++++++++++++++ .../MavenBuild/executedMojos_fr.properties | 16 ++++++------- .../index_fr.properties | 6 ++--- .../configure_fr.properties | 23 ++++++++++++++++++ 11 files changed, 118 insertions(+), 29 deletions(-) create mode 100644 core/src/main/resources/lib/layout/breadcrumbBar_fr.properties create mode 100644 core/src/main/resources/lib/layout/progressiveRendering_fr.properties create mode 100644 core/src/main/resources/lib/layout/task_fr.properties create mode 100644 test/src/main/resources/org/jvnet/hudson/test/ComputerConnectorTester/configure_fr.properties diff --git a/core/src/main/resources/hudson/AboutJenkins/index_fr.properties b/core/src/main/resources/hudson/AboutJenkins/index_fr.properties index a8b172e562..e58703411e 100644 --- a/core/src/main/resources/hudson/AboutJenkins/index_fr.properties +++ b/core/src/main/resources/hudson/AboutJenkins/index_fr.properties @@ -24,3 +24,4 @@ about=A propos de Jenkins {0} blurb=Jenkins est un serveur d''int\u00e9gration continue d\u00e9velopp\u00e9 par la communaut\u00e9 open-source. dependencies=Jenkins d\u00e9pend des librairies externes suivantes +plugin.dependencies=Licence et informations de d\u00e9pendance pour les plugins : diff --git a/core/src/main/resources/hudson/Messages_fr.properties b/core/src/main/resources/hudson/Messages_fr.properties index 9b8f5259c7..bcedd99861 100644 --- a/core/src/main/resources/hudson/Messages_fr.properties +++ b/core/src/main/resources/hudson/Messages_fr.properties @@ -50,5 +50,8 @@ Util.pastTime={0} FilePath.TildaDoesntWork=''~'' n''est support\u00e9 que sur les shells Unix. PluginManager.DisplayName=Gestion des plugins +PluginManager.PortNotANumber=Le port n''est pas un nombre +PluginManager.PortNotInRange=Le port n''est pas dans l''intervalle de {0} \u00e0 {1} + AboutJenkins.DisplayName=A propos de Jenkins AboutJenkins.Description=Afficher les informations de version et de licence diff --git a/core/src/main/resources/hudson/model/Messages_fr.properties b/core/src/main/resources/hudson/model/Messages_fr.properties index c347fd05d8..7cd7f753f7 100644 --- a/core/src/main/resources/hudson/model/Messages_fr.properties +++ b/core/src/main/resources/hudson/model/Messages_fr.properties @@ -122,7 +122,7 @@ Queue.WaitingForNextAvailableExecutor=En attente du prochain ex\u00e9cuteur disp Queue.WaitingForNextAvailableExecutorOn=En attente du prochain ex\u00e9cuteur disponible sur {0} Run.BuildAborted=Le build a \u00e9t\u00e9 annul\u00e9 Run.MarkedExplicitly=marqu\u00e9 explicitement pour conserv\u00e9 l''enregistrement -Run.Permissions.Title=Lancer +Run.Permissions.Title=Historique des builds Run.UnableToDelete=Impossible de supprimer {0}: {1} Run.DeletePermission.Description=\ Cette option permet aux utilisateurs de supprimer manuellement des builds sp\u00e9cifiques dans l''historique de build. @@ -139,7 +139,7 @@ Slave.UnableToLaunch=Impossible de lancer l''agent esclave pour {0} {1} Slave.UnixSlave=Ceci est un esclave Unix Slave.WindowsSlave=Ceci est un esclave Windows -View.Permissions.Title=Voir +View.Permissions.Title=Vues View.CreatePermission.Description=\ Ce droit permet aux utilisateurs de cr\u00e9er des nouvelles vues. View.DeletePermission.Description=\ diff --git a/core/src/main/resources/jenkins/model/Jenkins/legend_fr.properties b/core/src/main/resources/jenkins/model/Jenkins/legend_fr.properties index b1d2443b35..322a7d9d53 100644 --- a/core/src/main/resources/jenkins/model/Jenkins/legend_fr.properties +++ b/core/src/main/resources/jenkins/model/Jenkins/legend_fr.properties @@ -20,23 +20,17 @@ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. -grey=Le projet n''a jamais été construit avant ou est désactivé. +grey=Le projet n''a jamais \u00e9t\u00e9 construit avant ou est d\u00e9sactiv\u00e9. grey_anime=Le premier build du projet est en cours. -blue=Le dernier build s''est achevé avec succčs. -blue_anime=Le dernier build s''est achevé avec succčs. Un nouveau build est en cours. -yellow=Le dernier build s''est achevé avec succčs mais est instable. \ - Cela est utilisé principalement pour représenter des échecs sur les tests. -yellow_anime=Le dernier build s''est achevé avec succčs mais est instable. Un nouveau build est en cours. +blue=Le dernier build s''est achev\u00e9 avec succ\u00e8s. +blue_anime=Le dernier build s''est achev\u00e9 avec succ\u00e8s. Un nouveau build est en cours. +yellow=Le dernier build s''est achev\u00e9 avec succ\u00e8s mais est instable. \ + Cela est utilis\u00e9 principalement pour repr\u00e9senter des \u00e9checs sur les tests. +yellow_anime=Le dernier build s''est achev\u00e9 avec succ\u00e8s mais est instable. Un nouveau build est en cours. +red=Le dernier build est en \u00e9chec. +red_anime=Le dernier build est en \u00e9chec. Un nouveau build est en cours. health-81plus=La sant\u00E9 du projet est au dessus de 80%. Vous pouvez passer votre souris au dessus de l''ic\u00F4ne du projet pour plus d''informations. -red=Le dernier build est en échec. -red_anime=Le dernier build est en échec. Un nouveau build est en cours. health-61to80=La sant\u00E9 du projet est entre 60% et 80%. Vous pouvez passer votre souris au dessus de l''ic\u00F4ne du projet pour plus d''informations. -health-80plus=La stabilité du projet est d''au moins 80%. Placez la souris au-dessus de l''icône du projet pour plus de détails. health-41to60=La sant\u00E9 du projet est entre 40% et 60%. Vous pouvez passer votre souris au dessus de l''ic\u00F4ne du projet pour plus d''informations. -health-60to79=La stabilité du projet se situe entre 60% et 80%. Placez la souris au-dessus de l''icône du projet pour plus de détails. health-21to40=La sant\u00E9 du projet est entre 20% et 40%. Vous pouvez passer votre souris au dessus de l''ic\u00F4ne du projet pour plus d''informations. -health-40to59=La stabilité du projet se situe entre 40% et 60%. Placez la souris au-dessus de l''icône du projet pour plus de détails. health-00to20=La sant\u00E9 du projet est en dessous de 20%. Vous pouvez passer votre souris au dessus de l''ic\u00F4ne du projet pour plus d''informations. -health-20to39=La stabilité du projet se situe entre 20% et 40%. Placez la souris au-dessus de l''icône du projet pour plus de détails. -health-00to19=La stabilité du projet est de moins de 20%. Placez la souris au-dessus de l''icône du projet pour plus de détails. - diff --git a/core/src/main/resources/lib/layout/breadcrumbBar_fr.properties b/core/src/main/resources/lib/layout/breadcrumbBar_fr.properties new file mode 100644 index 0000000000..a9c2f374d8 --- /dev/null +++ b/core/src/main/resources/lib/layout/breadcrumbBar_fr.properties @@ -0,0 +1,24 @@ +# The MIT License +# +# Copyright (c) 2004-, Kohsuke Kawaguchi, Sun Microsystems, Inc., and a number of other of contributers +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +DISABLE\ AUTO\ REFRESH=ANNULER LE RAFRA\u00CECHISSEMENT AUTOMATIQUE +ENABLE\ AUTO\ REFRESH=ACTIVER LE RAFRA\u00CECHISSEMENT AUTOMATIQUE diff --git a/core/src/main/resources/lib/layout/layout_fr.properties b/core/src/main/resources/lib/layout/layout_fr.properties index 39b15e91f2..dbc67c5460 100644 --- a/core/src/main/resources/lib/layout/layout_fr.properties +++ b/core/src/main/resources/lib/layout/layout_fr.properties @@ -24,5 +24,3 @@ search=rechercher searchBox.url=http://wiki.jenkins-ci.org/display/JENKINS/Search+Box Page\ generated=Page g\u00E9n\u00E9r\u00E9e le logout=Se d\u00E9connecter -DISABLE\ AUTO\ REFRESH=ANNULER LE RAFRA\u00CECHISSEMENT AUTOMATIQUE -ENABLE\ AUTO\ REFRESH=ACTIVER LE RAFRA\u00CECHISSEMENT AUTOMATIQUE diff --git a/core/src/main/resources/lib/layout/progressiveRendering_fr.properties b/core/src/main/resources/lib/layout/progressiveRendering_fr.properties new file mode 100644 index 0000000000..c4e3e757fb --- /dev/null +++ b/core/src/main/resources/lib/layout/progressiveRendering_fr.properties @@ -0,0 +1,23 @@ +# The MIT License +# +# Copyright (c) 2013, Chunghwa Telecom Co., Ltd., Pei-Tang Huang +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +progressMessage=Calcul en cours. diff --git a/core/src/main/resources/lib/layout/task_fr.properties b/core/src/main/resources/lib/layout/task_fr.properties new file mode 100644 index 0000000000..7fae593429 --- /dev/null +++ b/core/src/main/resources/lib/layout/task_fr.properties @@ -0,0 +1,23 @@ +# The MIT License +# +# Copyright (c) 2013, Seiji Sogabe +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +Done.=Fait. diff --git a/maven-plugin/src/main/resources/hudson/maven/MavenBuild/executedMojos_fr.properties b/maven-plugin/src/main/resources/hudson/maven/MavenBuild/executedMojos_fr.properties index 05c0cdf8b5..8516b26c8a 100644 --- a/maven-plugin/src/main/resources/hudson/maven/MavenBuild/executedMojos_fr.properties +++ b/maven-plugin/src/main/resources/hudson/maven/MavenBuild/executedMojos_fr.properties @@ -21,12 +21,12 @@ # THE SOFTWARE. Build\ in\ progress.=Build en cours -No\ mojos\ executed.=Aucun mojo n''a été exécuté -Plugin= -Version= +No\ mojos\ executed.=Aucun mojo n''a \u00e9t\u00e9 ex\u00e9cut\u00e9 +Plugin=Plugin +Version=Version Goal=Goal -Execution=Exécution -Duration=Durée -Fingerprint=Empreinte numérique -fingerprint=empreinte numérique -Executed\ Mojos=Mojos exécutés +Execution=Ex\u00e9cution +Duration=Dur\u00e9e +Fingerprint=Empreinte num\u00e9rique +fingerprint=empreinte num\u00e9rique +Executed\ Mojos=Mojos ex\u00e9cut\u00e9s diff --git a/maven-plugin/src/main/resources/hudson/maven/reporters/MavenAbstractArtifactRecord/index_fr.properties b/maven-plugin/src/main/resources/hudson/maven/reporters/MavenAbstractArtifactRecord/index_fr.properties index a767ce1d78..4487755bc1 100644 --- a/maven-plugin/src/main/resources/hudson/maven/reporters/MavenAbstractArtifactRecord/index_fr.properties +++ b/maven-plugin/src/main/resources/hudson/maven/reporters/MavenAbstractArtifactRecord/index_fr.properties @@ -20,6 +20,6 @@ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. -This\ page\ allows\ you\ to\ redeploy\ the\ build\ artifacts\ to\ a\ repository\ after\ the\ fact.=Cette page vous permet de redéployer les artefacts vers un repository aprčs coup. -Redeploy\ Artifacts=Redéployer les artefacts -OK= +This\ page\ allows\ you\ to\ redeploy\ the\ build\ artifacts\ to\ a\ repository\ after\ the\ fact.=Cette page vous permet de red\u00e9ployer les artefacts vers un repository apr\u00e8s coup. +Redeploy\ Artifacts=Red\u00e9ployer les artefacts +OK=OK diff --git a/test/src/main/resources/org/jvnet/hudson/test/ComputerConnectorTester/configure_fr.properties b/test/src/main/resources/org/jvnet/hudson/test/ComputerConnectorTester/configure_fr.properties new file mode 100644 index 0000000000..87c0ef6252 --- /dev/null +++ b/test/src/main/resources/org/jvnet/hudson/test/ComputerConnectorTester/configure_fr.properties @@ -0,0 +1,23 @@ +# The MIT License +# +# Copyright (c) 2004-, Kohsuke Kawaguchi, Sun Microsystems, Inc., and a number of other of contributers +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +Save=Sauvegarder From 476fe22d6ed0ce94493b7984605764a0e245ca3c Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Fri, 24 May 2013 10:10:36 -0400 Subject: [PATCH 132/233] hashify was in 1.510, not 1.509. --- core/src/main/java/hudson/scheduler/CronTab.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/main/java/hudson/scheduler/CronTab.java b/core/src/main/java/hudson/scheduler/CronTab.java index ec8c4ffb43..14ad347a00 100644 --- a/core/src/main/java/hudson/scheduler/CronTab.java +++ b/core/src/main/java/hudson/scheduler/CronTab.java @@ -442,7 +442,7 @@ public final class CronTab { * Checks a prospective crontab specification to see if it could benefit from balanced hashes. * @param spec a (legal) spec * @return a similar spec that uses a hash, if such a transformation is necessary; null if it is OK as is - * @since 1.509 + * @since 1.510 */ public static @CheckForNull String hashify(String spec) { if (spec.contains("H")) { From 6cb7fc4ae354ae084a0719f4a6d2ef409e19b1ee Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Fri, 24 May 2013 11:39:05 -0400 Subject: [PATCH 133/233] JUnit 4 --- .../test/java/hudson/model/DisplayNameTest.java | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/test/src/test/java/hudson/model/DisplayNameTest.java b/test/src/test/java/hudson/model/DisplayNameTest.java index ba557e202d..afe508e1ac 100644 --- a/test/src/test/java/hudson/model/DisplayNameTest.java +++ b/test/src/test/java/hudson/model/DisplayNameTest.java @@ -26,20 +26,23 @@ package hudson.model; import jenkins.model.Jenkins; import org.junit.Assert; +import org.junit.Rule; import org.junit.Test; -import org.jvnet.hudson.test.HudsonTestCase; +import org.jvnet.hudson.test.JenkinsRule; /** * @author kingfai * */ -public class DisplayNameTest extends HudsonTestCase { +public class DisplayNameTest { + + @Rule public JenkinsRule j = new JenkinsRule(); @Test public void testRenameJobWithNoDisplayName() throws Exception { final String projectName = "projectName"; final String newProjectName = "newProjectName"; - FreeStyleProject project = createFreeStyleProject(projectName); + FreeStyleProject project = j.createFreeStyleProject(projectName); Assert.assertEquals(projectName, project.getDisplayName()); project.renameTo(newProjectName); @@ -51,7 +54,7 @@ public class DisplayNameTest extends HudsonTestCase { final String projectName = "projectName"; final String newProjectName = "newProjectName"; final String displayName = "displayName"; - FreeStyleProject project = createFreeStyleProject(projectName); + FreeStyleProject project = j.createFreeStyleProject(projectName); project.setDisplayName(displayName); Assert.assertEquals(displayName, project.getDisplayName()); @@ -64,7 +67,7 @@ public class DisplayNameTest extends HudsonTestCase { public void testCopyJobWithNoDisplayName() throws Exception { final String projectName = "projectName"; final String newProjectName = "newProjectName"; - FreeStyleProject project = createFreeStyleProject(projectName); + FreeStyleProject project = j.createFreeStyleProject(projectName); Assert.assertEquals(projectName, project.getDisplayName()); AbstractProject newProject = Jenkins.getInstance().copy((AbstractProject)project, newProjectName); @@ -78,7 +81,7 @@ public class DisplayNameTest extends HudsonTestCase { final String projectName = "projectName"; final String newProjectName = "newProjectName"; final String oldDisplayName = "oldDisplayName"; - FreeStyleProject project = createFreeStyleProject(projectName); + FreeStyleProject project = j.createFreeStyleProject(projectName); project.setDisplayName(oldDisplayName); Assert.assertEquals(oldDisplayName, project.getDisplayName()); From 04e2ccade6c831578bdd32b5e5982cf150f635f4 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Fri, 24 May 2013 12:06:37 -0400 Subject: [PATCH 134/233] [FIXED JENKINS-18074] Avoid clearing AbstractItem.displayName when the new parent ItemGroup is different. --- changelog.html | 3 +++ .../java/hudson/model/DisplayNameListener.java | 2 +- .../java/org/jvnet/hudson/test/MockFolder.java | 11 +++++++++++ .../test/java/hudson/model/DisplayNameTest.java | 14 ++++++++++++++ 4 files changed, 29 insertions(+), 1 deletion(-) diff --git a/changelog.html b/changelog.html index 4620974138..b8ad7e6a44 100644 --- a/changelog.html +++ b/changelog.html @@ -61,6 +61,9 @@ Upcoming changes
        • Allow filtering of the Run parameter build list by result. (issue 7280) +
        • + When copying a folder, the display names of contained jobs were gratuitously cleared. + (issue 18074)
        • “Recurse in subfolders” option for list views produced exceptions when used with native Maven projects. (issue 18025) diff --git a/core/src/main/java/hudson/model/DisplayNameListener.java b/core/src/main/java/hudson/model/DisplayNameListener.java index 93ddbdea05..8a41ccf4a8 100644 --- a/core/src/main/java/hudson/model/DisplayNameListener.java +++ b/core/src/main/java/hudson/model/DisplayNameListener.java @@ -50,7 +50,7 @@ public class DisplayNameListener extends ItemListener { */ public void onCopied(Item src, Item item) { // bug 5056825 - Display name field should be cleared when you copy a job. - if(item instanceof AbstractItem) { + if(item instanceof AbstractItem && src.getParent() == item.getParent()) { AbstractItem dest = (AbstractItem)item; try { dest.setDisplayName(null); diff --git a/test/src/main/java/org/jvnet/hudson/test/MockFolder.java b/test/src/main/java/org/jvnet/hudson/test/MockFolder.java index 50d5d17057..628cf92325 100644 --- a/test/src/main/java/org/jvnet/hudson/test/MockFolder.java +++ b/test/src/main/java/org/jvnet/hudson/test/MockFolder.java @@ -136,6 +136,17 @@ public class MockFolder extends AbstractItem implements ModifiableTopLevelItemGr return mixin().copy(src, name); } + @Override public void onCopiedFrom(Item src) { + super.onCopiedFrom(src); + for (TopLevelItem item : ((MockFolder) src).getItems()) { + try { + copy(item, item.getName()); + } catch (IOException x) { + assert false : x; + } + } + } + @Override public TopLevelItem createProjectFromXML(String name, InputStream xml) throws IOException { return mixin().createProjectFromXML(name, xml); } diff --git a/test/src/test/java/hudson/model/DisplayNameTest.java b/test/src/test/java/hudson/model/DisplayNameTest.java index afe508e1ac..38fd8a0610 100644 --- a/test/src/test/java/hudson/model/DisplayNameTest.java +++ b/test/src/test/java/hudson/model/DisplayNameTest.java @@ -28,7 +28,9 @@ import jenkins.model.Jenkins; import org.junit.Assert; import org.junit.Rule; import org.junit.Test; +import org.jvnet.hudson.test.Bug; import org.jvnet.hudson.test.JenkinsRule; +import org.jvnet.hudson.test.MockFolder; /** * @author kingfai @@ -90,4 +92,16 @@ public class DisplayNameTest { Assert.assertEquals(newProjectName, newProject.getDisplayName()); } + + @Bug(18074) + @Test public void copyJobWithDisplayNameToDifferentFolder() throws Exception { + MockFolder d1 = j.createFolder("d1"); + FreeStyleProject job = d1.createProject(FreeStyleProject.class, "job"); + job.setDisplayName("My Job"); + MockFolder d2 = j.jenkins.copy(d1, "d2"); + FreeStyleProject j2 = (FreeStyleProject) d2.getItem("job"); + Assert.assertNotNull(j2); + Assert.assertEquals("My Job", j2.getDisplayName()); + } + } From 8aed6623900e8827b587389e6af7958f05ecab87 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Fri, 24 May 2013 13:47:29 -0400 Subject: [PATCH 135/233] [JENKINS-18074] Fixed unit test by making StubJob.getParent forgiving. https://ci.jenkins-ci.org/job/jenkins_main_trunk/2545/testReport/junit/hudson.model/DisplayNameListenerTest/testOnCopied/ --- core/src/test/java/hudson/model/StubJob.java | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/core/src/test/java/hudson/model/StubJob.java b/core/src/test/java/hudson/model/StubJob.java index cc5224aae6..7f3b1dda7d 100644 --- a/core/src/test/java/hudson/model/StubJob.java +++ b/core/src/test/java/hudson/model/StubJob.java @@ -28,8 +28,9 @@ import java.util.SortedMap; /** * @author kingfai - * + * @deprecated Does not behave very consistently. Either write a real functional test with {@code JenkinsRule}, or use PowerMock/Mockito. */ +@Deprecated @SuppressWarnings({ "rawtypes", "unchecked" }) class StubJob extends Job { @@ -69,4 +70,8 @@ class StubJob extends Job { } + @Override public ItemGroup getParent() { + return null; + } + } From 20b80cc6a05520303c500c4d6cd52361fa9e94c2 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Fri, 24 May 2013 16:38:45 -0400 Subject: [PATCH 136/233] Display classLoadingPrefetchCacheCount. --- .../main/java/hudson/slaves/SlaveComputer.java | 18 ++++++++++++++++++ .../slaves/SlaveComputer/statistics.groovy | 10 +++++++++- pom.xml | 2 +- 3 files changed, 28 insertions(+), 2 deletions(-) diff --git a/core/src/main/java/hudson/slaves/SlaveComputer.java b/core/src/main/java/hudson/slaves/SlaveComputer.java index cdffb6d5f7..97a2578f44 100644 --- a/core/src/main/java/hudson/slaves/SlaveComputer.java +++ b/core/src/main/java/hudson/slaves/SlaveComputer.java @@ -348,6 +348,18 @@ public class SlaveComputer extends Computer { return channel.call(new LoadingCount(false)); } + /** + * Shows {@link Channel#classLoadingPrefetchCacheCount}. + * @return -1 in case that capability is not supported + * @since XXX prefetch-JENKINS-15120 + */ + public int getClassLoadingPrefetchCacheCount() throws IOException, InterruptedException { + if (!channel.remoteCapability.supportsPrefetch()) { + return -1; + } + return channel.call(new LoadingPrefetchCacheCount()); + } + /** * Shows {@link Channel#resourceLoadingCount}. * @since 1.495 @@ -383,6 +395,12 @@ public class SlaveComputer extends Computer { } } + static class LoadingPrefetchCacheCount implements Callable { + @Override public Integer call() { + return Channel.current().classLoadingPrefetchCacheCount.get(); + } + } + static class LoadingTime implements Callable { private final boolean resource; LoadingTime(boolean resource) { diff --git a/core/src/main/resources/hudson/slaves/SlaveComputer/statistics.groovy b/core/src/main/resources/hudson/slaves/SlaveComputer/statistics.groovy index f0b62d524e..6a801364f9 100644 --- a/core/src/main/resources/hudson/slaves/SlaveComputer/statistics.groovy +++ b/core/src/main/resources/hudson/slaves/SlaveComputer/statistics.groovy @@ -10,7 +10,15 @@ table(class: 'bigtable') { tr { td _('Classes') td(style: right) {text(fmt.format(my.classLoadingTime / 1000000000))} - td(style: right) {text(my.classLoadingCount)} + td(style: right) { + text(my.classLoadingCount) + def classLoadingPrefetchCacheCount = my.classLoadingPrefetchCacheCount; + if (classLoadingPrefetchCacheCount != -1) { + text(_(' (prefetch cache: ')) + text(classLoadingPrefetchCacheCount) + text(_(')')) + } + } } tr { td _('Resources') diff --git a/pom.xml b/pom.xml index 45a72f733f..88c02655e1 100644 --- a/pom.xml +++ b/pom.xml @@ -175,7 +175,7 @@ THE SOFTWARE. org.jenkins-ci.main remoting - 2.23 + 2.24-SNAPSHOT From aec296ef756d6f1c7c64374df343752f26b12c97 Mon Sep 17 00:00:00 2001 From: Damien Finck Date: Fri, 24 May 2013 23:05:18 +0200 Subject: [PATCH 137/233] Added French translation --- .../config_fr.properties | 2 +- .../FileParameterValue/value_fr.properties | 23 +++++++++++++++ .../newJobDetail_fr.properties | 5 ++-- .../model/Job/buildTimeTrend_fr.properties | 6 ++-- .../hudson/model/Job/configure_fr.properties | 2 ++ .../hudson/model/Job/index_fr.properties | 23 +++++++++++++++ .../ParametersAction/index_fr.properties | 2 +- .../index_fr.properties | 5 ++-- .../config_fr.properties | 3 +- .../labels/LabelAtom/configure_fr.properties | 25 +++++++++++++++++ .../message_fr.properties | 28 +++++++++++++++++++ .../resources/lib/form/apply_fr.properties | 23 +++++++++++++++ .../lib/form/booleanRadio_fr.properties | 24 ++++++++++++++++ .../breadcrumb-config-outline_fr.properties | 23 +++++++++++++++ .../lib/form/hetero-list_fr.properties | 23 +++++++++++++++ 15 files changed, 207 insertions(+), 10 deletions(-) create mode 100644 core/src/main/resources/hudson/model/FileParameterValue/value_fr.properties create mode 100644 core/src/main/resources/hudson/model/Job/index_fr.properties create mode 100644 core/src/main/resources/hudson/model/labels/LabelAtom/configure_fr.properties create mode 100644 core/src/main/resources/jenkins/diagnostics/SecurityIsOffMonitor/message_fr.properties create mode 100644 core/src/main/resources/lib/form/apply_fr.properties create mode 100644 core/src/main/resources/lib/form/booleanRadio_fr.properties create mode 100644 core/src/main/resources/lib/form/breadcrumb-config-outline_fr.properties create mode 100644 core/src/main/resources/lib/form/hetero-list_fr.properties diff --git a/core/src/main/resources/hudson/model/FileParameterDefinition/config_fr.properties b/core/src/main/resources/hudson/model/FileParameterDefinition/config_fr.properties index 2234923d9b..90e6149fb3 100644 --- a/core/src/main/resources/hudson/model/FileParameterDefinition/config_fr.properties +++ b/core/src/main/resources/hudson/model/FileParameterDefinition/config_fr.properties @@ -21,4 +21,4 @@ # THE SOFTWARE. File\ location=Emplacement du fichier -Description= +Description=Description diff --git a/core/src/main/resources/hudson/model/FileParameterValue/value_fr.properties b/core/src/main/resources/hudson/model/FileParameterValue/value_fr.properties new file mode 100644 index 0000000000..577c9ddf46 --- /dev/null +++ b/core/src/main/resources/hudson/model/FileParameterValue/value_fr.properties @@ -0,0 +1,23 @@ +# The MIT License +# +# Copyright (c) 2004-2013, Seiji Sogabe +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +view=vues diff --git a/core/src/main/resources/hudson/model/FreeStyleProject/newJobDetail_fr.properties b/core/src/main/resources/hudson/model/FreeStyleProject/newJobDetail_fr.properties index 854403a6f5..a219b895b0 100644 --- a/core/src/main/resources/hudson/model/FreeStyleProject/newJobDetail_fr.properties +++ b/core/src/main/resources/hudson/model/FreeStyleProject/newJobDetail_fr.properties @@ -20,5 +20,6 @@ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. -body=Ceci est la fonction principale de Hudson qui sert \u00E0 builder (construire) votre projet.
          Vous pouvez int\u00E9grer tous les outils de gestion de version avec tous les syst\u00E8mes de build.
          Il est m\u00EAme possible d''''utiliser Hudson pour tout autre chose qu''''un build logiciel. - +body=Ceci est la fonction principale de Jenkins qui sert \u00E0 builder (construire) votre projet.
          \ + Vous pouvez int\u00E9grer tous les outils de gestion de version avec tous les syst\u00E8mes de build.
          \ + Il est m\u00EAme possible d''utiliser Jenkins pour tout autre chose qu''un build logiciel. diff --git a/core/src/main/resources/hudson/model/Job/buildTimeTrend_fr.properties b/core/src/main/resources/hudson/model/Job/buildTimeTrend_fr.properties index 11b3336883..58e24c8c9b 100644 --- a/core/src/main/resources/hudson/model/Job/buildTimeTrend_fr.properties +++ b/core/src/main/resources/hudson/model/Job/buildTimeTrend_fr.properties @@ -21,9 +21,9 @@ # THE SOFTWARE. Timeline=Chronologie -title={0} Courbe de tendance de la durée du build +title={0} Courbe de tendance de la dur\u00e9e du build Build=Build Build\ Time\ Trend=Tendance des temps des builds -Duration=Durée +Duration=Dur\u00e9e Slave=Esclave -More\ than\ 1\ builds\ are\ needed\ for\ the\ trend\ report.=Plus de 1 build est nécessaire pour le rapport de tendance. +More\ than\ 1\ builds\ are\ needed\ for\ the\ trend\ report.=Plus de 1 build est n\u00e9cessaire pour le rapport de tendance. diff --git a/core/src/main/resources/hudson/model/Job/configure_fr.properties b/core/src/main/resources/hudson/model/Job/configure_fr.properties index 964fa78a28..a91e9827ce 100644 --- a/core/src/main/resources/hudson/model/Job/configure_fr.properties +++ b/core/src/main/resources/hudson/model/Job/configure_fr.properties @@ -24,3 +24,5 @@ name=Nom du {0} Description=Description Discard\ Old\ Builds=Supprimer les anciens builds Save=Sauver +LOADING=CHARGEMENT +Strategy=Strat\u00e9gie diff --git a/core/src/main/resources/hudson/model/Job/index_fr.properties b/core/src/main/resources/hudson/model/Job/index_fr.properties new file mode 100644 index 0000000000..fd2b2abce8 --- /dev/null +++ b/core/src/main/resources/hudson/model/Job/index_fr.properties @@ -0,0 +1,23 @@ +# The MIT License +# +# Copyright (c) 2004-2012, Sun Microsystems, Inc., Kohsuke Kawaguchi, Seiji Sogabe, id:cactusman +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +Project\ name=Nom du projet diff --git a/core/src/main/resources/hudson/model/ParametersAction/index_fr.properties b/core/src/main/resources/hudson/model/ParametersAction/index_fr.properties index ca8e3995b5..4a0d378cf0 100644 --- a/core/src/main/resources/hudson/model/ParametersAction/index_fr.properties +++ b/core/src/main/resources/hudson/model/ParametersAction/index_fr.properties @@ -21,4 +21,4 @@ # THE SOFTWARE. Parameters=Paramčtres -Build= +Build=Build diff --git a/core/src/main/resources/hudson/model/ParametersDefinitionProperty/index_fr.properties b/core/src/main/resources/hudson/model/ParametersDefinitionProperty/index_fr.properties index 94ebf469b5..dd13747fab 100644 --- a/core/src/main/resources/hudson/model/ParametersDefinitionProperty/index_fr.properties +++ b/core/src/main/resources/hudson/model/ParametersDefinitionProperty/index_fr.properties @@ -20,5 +20,6 @@ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. -description=Ce build nécessite des paramčtres: -Build= +description=Ce build n\u00e9cessite des param\u00e8tres : +Build=Build +LOADING=CHARGEMENT diff --git a/core/src/main/resources/hudson/model/PasswordParameterDefinition/config_fr.properties b/core/src/main/resources/hudson/model/PasswordParameterDefinition/config_fr.properties index 051ef7d16e..215680b6c5 100644 --- a/core/src/main/resources/hudson/model/PasswordParameterDefinition/config_fr.properties +++ b/core/src/main/resources/hudson/model/PasswordParameterDefinition/config_fr.properties @@ -20,5 +20,6 @@ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. -Default\ Value=Valeur par d\u00E9faut Name=Nom +Default\ Value=Valeur par d\u00E9faut +Description=Description diff --git a/core/src/main/resources/hudson/model/labels/LabelAtom/configure_fr.properties b/core/src/main/resources/hudson/model/labels/LabelAtom/configure_fr.properties new file mode 100644 index 0000000000..781cda7c2a --- /dev/null +++ b/core/src/main/resources/hudson/model/labels/LabelAtom/configure_fr.properties @@ -0,0 +1,25 @@ +# The MIT License +# +# Copyright (c) 2011, Seiji Sogabe +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +Name=Nom +Save=Sauver +title={0} Configuration diff --git a/core/src/main/resources/jenkins/diagnostics/SecurityIsOffMonitor/message_fr.properties b/core/src/main/resources/jenkins/diagnostics/SecurityIsOffMonitor/message_fr.properties new file mode 100644 index 0000000000..7225894844 --- /dev/null +++ b/core/src/main/resources/jenkins/diagnostics/SecurityIsOffMonitor/message_fr.properties @@ -0,0 +1,28 @@ +# +# The MIT License +# +# Copyright (c) 2013, Kohsuke Kawaguchi +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. +# + +blurb=La non s\u00e9curisation de Jenkins permet \u00e0 quiconque sur le r\u00e9seau de lancer des processus en votre nom. \ + Envisager au moins une authentification permettant de d\u00e9courager les abus. +Setup\ Security=Configuration de la s\u00e9curit\u00e9 +Dismiss=Cacher ce message diff --git a/core/src/main/resources/lib/form/apply_fr.properties b/core/src/main/resources/lib/form/apply_fr.properties new file mode 100644 index 0000000000..77842f0cc6 --- /dev/null +++ b/core/src/main/resources/lib/form/apply_fr.properties @@ -0,0 +1,23 @@ +# The MIT License +# +# Copyright (c) 2012, Kohsuke Kawaguchi, Sun Microsystems, Inc., and a number of other of contributers +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +Apply=Appliquer diff --git a/core/src/main/resources/lib/form/booleanRadio_fr.properties b/core/src/main/resources/lib/form/booleanRadio_fr.properties new file mode 100644 index 0000000000..d0869be48e --- /dev/null +++ b/core/src/main/resources/lib/form/booleanRadio_fr.properties @@ -0,0 +1,24 @@ +# The MIT License +# +# Copyright (c) 2004-2010, Sun Microsystems, Inc. +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +Yes=Oui +No=Non diff --git a/core/src/main/resources/lib/form/breadcrumb-config-outline_fr.properties b/core/src/main/resources/lib/form/breadcrumb-config-outline_fr.properties new file mode 100644 index 0000000000..e212b91926 --- /dev/null +++ b/core/src/main/resources/lib/form/breadcrumb-config-outline_fr.properties @@ -0,0 +1,23 @@ +# The MIT License +# +# Copyright (c) 2012, Seiji Sogabe +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +configuration=configuration diff --git a/core/src/main/resources/lib/form/hetero-list_fr.properties b/core/src/main/resources/lib/form/hetero-list_fr.properties new file mode 100644 index 0000000000..0bbfae5199 --- /dev/null +++ b/core/src/main/resources/lib/form/hetero-list_fr.properties @@ -0,0 +1,23 @@ +# The MIT License +# +# Copyright (c) 2004-2010, Sun Microsystems, Inc. +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +Add=Ajouter From a20d8954848b75307f4f744f723afdb00c54b71e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ronald=20Tschal=C3=A4r?= Date: Fri, 24 May 2013 23:40:30 -0700 Subject: [PATCH 138/233] Add support for scalatest-maven-plugin test results. --- .../java/hudson/maven/reporters/TestMojo.java | 33 ++++- .../hudson/maven/reporters/TestMojoTest.java | 138 ++++++++++++++++++ 2 files changed, 170 insertions(+), 1 deletion(-) diff --git a/maven-plugin/src/main/java/hudson/maven/reporters/TestMojo.java b/maven-plugin/src/main/java/hudson/maven/reporters/TestMojo.java index 3319d44f67..b91a0c0925 100644 --- a/maven-plugin/src/main/java/hudson/maven/reporters/TestMojo.java +++ b/maven-plugin/src/main/java/hudson/maven/reporters/TestMojo.java @@ -69,7 +69,38 @@ enum TestMojo { return null; } }, - TOOLKIT_RESOLVER_PLUGIN("org.terracotta.maven.plugins", "toolkit-resolver-plugin", "toolkit-resolve-test","reportsDirectory"); + TOOLKIT_RESOLVER_PLUGIN("org.terracotta.maven.plugins", "toolkit-resolver-plugin", "toolkit-resolve-test","reportsDirectory"), + SCALATEST_MAVEN_PLUGIN("org.scalatest", "scalatest-maven-plugin", "test", null) { + @Override + public Iterable getReportFiles(MavenProject pom, MojoInfo mojo) + throws ComponentConfigurationException { + /* scalatest-maven-plugin has a configuration entry 'junitxml' which is a + * comma-separated list of directories; commas may be escaped with a backslash + * (\,). Each directory is taken relative to the reportsDirectory. + */ + File reportsDir = mojo.getConfigurationValue("reportsDirectory", File.class); + String junitDirs = mojo.getConfigurationValue("junitxml", String.class); + + if (junitDirs == null || junitDirs.trim().length() == 0) { + return null; + } + + // split along non-escaped commas + String[] junitDirsList = junitDirs.trim().split("(? 0) { + // unescape escaped commas + String junitDirName = dir.trim().replaceAll("\\\\,", ","); + File junitDir = new File(reportsDir, junitDirName); + if (junitDir.exists()) { + return super.getReportFiles(junitDir, super.getFileSet(junitDir)); + } + } + } + + return null; + } + }; private String reportDirectoryConfigKey; private Key key; diff --git a/maven-plugin/src/test/java/hudson/maven/reporters/TestMojoTest.java b/maven-plugin/src/test/java/hudson/maven/reporters/TestMojoTest.java index 5cfd8a643b..949510b866 100644 --- a/maven-plugin/src/test/java/hudson/maven/reporters/TestMojoTest.java +++ b/maven-plugin/src/test/java/hudson/maven/reporters/TestMojoTest.java @@ -2,6 +2,8 @@ package hudson.maven.reporters; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertNull; +import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.when; @@ -81,4 +83,140 @@ public class TestMojoTest { testResults.delete(); } } + + @Test + public void testScalatestMavenPluginNoJunitxml() throws Exception { + runScalatestPluginTestNoEntries(null); + } + + @Test + public void testScalatestMavenPluginEmptyJunitxml() throws Exception { + runScalatestPluginTestNoEntries(""); + } + + @Test + public void testScalatestMavenPluginJunitxmlHasListOfEmptyEntries() throws Exception { + runScalatestPluginTestNoEntries(", "); + } + + @Test + public void testScalatestMavenPluginJunitxmlEntryDoesntExist() throws Exception { + runScalatestPluginTestNoEntries("foo"); + } + + @Test + public void testScalatestMavenPluginJunitxmlHasOneEntry() throws Exception { + runScalatestPluginTestOneEntry("ut-xml", "ut-xml"); + } + + @Test + public void testScalatestMavenPluginJunitxmlHasOneEntryAndTrailingDummy() throws Exception { + runScalatestPluginTestOneEntry("ut-xml,", "ut-xml"); + } + + @Test + public void testScalatestMavenPluginJunitxmlHasOneEntryAndLeadingDummy() throws Exception { + runScalatestPluginTestOneEntry(",ut-xml", "ut-xml"); + } + + @Test + public void testScalatestMavenPluginJunitxmlHasOneEntryAndDummiesOnBothEnds() throws Exception { + runScalatestPluginTestOneEntry(",ut-xml,", "ut-xml"); + } + + @Test + public void testScalatestMavenPluginJunitxmlHasMultipleEntries() throws Exception { + runScalatestPluginTestOneEntry("ut-xml, foo, baz", "ut-xml"); + } + + @Test + public void testScalatestMavenPluginJunitxmlHasMultipleEntriesAndFirstOneInvalid() + throws Exception { + runScalatestPluginTestOneEntry("foo, ut-xml, baz", "ut-xml"); + } + + @Test + public void testScalatestMavenPluginJunitxmlHasMultipleEntriesWithEscapedCommas() + throws Exception { + runScalatestPluginTestOneEntry("ut\\,xml, foo, baz", "ut,xml"); + } + + private void runScalatestPluginTestNoEntries(final String junitxml) throws Exception { + runScalatestPluginTest("", new ScalatestPluginTest() { + public void run(MojoInfoBuilder mojoBuilder, MavenProject pom, + String testResultsName) throws Exception { + if (junitxml != null) + mojoBuilder = mojoBuilder.configValue("junitxml", junitxml); + MojoInfo mojoInfo = mojoBuilder.build(); + + Iterable files = + TestMojo.SCALATEST_MAVEN_PLUGIN.getReportFiles(pom, mojoInfo); + assertNull("unexpected report files returned", files); + } + }); + } + + private void runScalatestPluginTestOneEntry(final String junitxml, String expectedDir) + throws Exception { + runScalatestPluginTest(expectedDir, new ScalatestPluginTest() { + public void run(MojoInfoBuilder mojoBuilder, MavenProject pom, + String testResultsName) throws Exception { + MojoInfo mojoInfo = mojoBuilder.configValue("junitxml", junitxml).build(); + + Iterable files = + TestMojo.SCALATEST_MAVEN_PLUGIN.getReportFiles(pom, mojoInfo); + assertHasOneFile(files, testResultsName); + } + }); + } + + private void assertHasOneFile(Iterable files, String expectedFile) { + assertNotNull("no report files returned", files); + + boolean found = false; + for (File file : files) { + assertFalse("unexpected report files returned: " + file, found); + assertEquals(expectedFile, file.getName()); + found = true; + } + assertTrue("report file not found", found); + } + + private void runScalatestPluginTest(String junitXmlDirName, ScalatestPluginTest test) + throws Exception { + final String testResultsName = "TEST-are-we-foobared.xml"; + + File testDir = hudson.Util.createTempDir(); + File targetDir = new File(testDir, "target"); + File reportsDir = new File(targetDir, "scalatest-reports"); + File junitXmlDir = new File(reportsDir, junitXmlDirName); + assertTrue(junitXmlDir.mkdirs()); + + MojoInfoBuilder mojoBuilder = + MojoInfoBuilder.mojoBuilder("org.scalatest", "scalatest-maven-plugin", "test") + .configValue("reportsDirectory", reportsDir.toString()); + + File testResults = new File(junitXmlDir, testResultsName); + try { + FileWriter fw = new FileWriter(testResults, false); + fw.write("this is a fake junit reports file"); + fw.close(); + + MavenProject pom = mock(MavenProject.class); + when(pom.getBasedir()).thenReturn(testDir); + + Build build = mock(Build.class); + when(build.getDirectory()).thenReturn(targetDir.getAbsolutePath()); + when(pom.getBuild()).thenReturn(build); + + test.run(mojoBuilder, pom, testResultsName); + } finally { + testResults.delete(); + } + } + + private static interface ScalatestPluginTest { + public void run(MojoInfoBuilder mojoBuilder, MavenProject pom, + String testResultsName) throws Exception; + } } From 904342a695868137fe8fcdce8bf44496c2120e9c Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Mon, 27 May 2013 22:23:16 -0700 Subject: [PATCH 139/233] [maven-release-plugin] prepare release jenkins-1.516 --- cli/pom.xml | 2 +- core/pom.xml | 2 +- maven-plugin/pom.xml | 2 +- plugins/pom.xml | 12 ++++++------ pom.xml | 2 +- test/pom.xml | 2 +- ui-samples-plugin/pom.xml | 2 +- war/pom.xml | 2 +- 8 files changed, 13 insertions(+), 13 deletions(-) diff --git a/cli/pom.xml b/cli/pom.xml index e0dca53c38..08044b27a4 100644 --- a/cli/pom.xml +++ b/cli/pom.xml @@ -5,7 +5,7 @@ pom org.jenkins-ci.main - 1.516-SNAPSHOT + 1.516 cli diff --git a/core/pom.xml b/core/pom.xml index a5636bf7d8..6e5e7fa5c7 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.516-SNAPSHOT + 1.516 ../pom.xml diff --git a/maven-plugin/pom.xml b/maven-plugin/pom.xml index 298856a700..735361bd9a 100644 --- a/maven-plugin/pom.xml +++ b/maven-plugin/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.516-SNAPSHOT + 1.516 maven-plugin diff --git a/plugins/pom.xml b/plugins/pom.xml index 7275ce48bc..ee7ea041fd 100644 --- a/plugins/pom.xml +++ b/plugins/pom.xml @@ -11,7 +11,7 @@ org.jenkins-ci.plugins plugin Jenkins plugin POM - 1.516-SNAPSHOT + 1.516 pom org.jenkins-ci.main maven-plugin - 1.516-SNAPSHOT + 1.516
          @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.516-SNAPSHOT + 1.516 test org.jenkins-ci.main jenkins-core - 1.516-SNAPSHOT + 1.516 provided org.jenkins-ci.main jenkins-test-harness - 1.516-SNAPSHOT + 1.516 test org.jenkins-ci.main ui-samples-plugin - 1.516-SNAPSHOT + 1.516 test org.jenkins-ci.main maven-plugin - 1.516 + 1.517-SNAPSHOT @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.516 + 1.517-SNAPSHOT test org.jenkins-ci.main jenkins-core - 1.516 + 1.517-SNAPSHOT provided org.jenkins-ci.main jenkins-test-harness - 1.516 + 1.517-SNAPSHOT test org.jenkins-ci.main ui-samples-plugin - 1.516 + 1.517-SNAPSHOT test +

          What's new in 1.516 (2013/05/27)

          • NPE from Run.getDynamic. @@ -76,7 +79,6 @@ Upcoming changes Errors in init.groovy halted startup; changed to just log a warning. (issue 17933)
          -

          What's new in 1.515 (2013/05/18)

          • From 023b1f88b343dc26740188b861bd4dab085ad662 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Mon, 27 May 2013 23:06:50 -0700 Subject: [PATCH 142/233] updated changelog as a part of the release --- debian/debian/changelog | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/debian/debian/changelog b/debian/debian/changelog index 330d8d700c..11a994920a 100644 --- a/debian/debian/changelog +++ b/debian/debian/changelog @@ -1,3 +1,9 @@ +jenkins (1.516) unstable; urgency=low + + * See http://jenkins-ci.org/changelog for more details. + + -- Kohsuke Kawaguchi Mon, 27 May 2013 22:47:35 -0700 + jenkins (1.515) unstable; urgency=low * See http://jenkins-ci.org/changelog for more details. From 1b25f63351fb7a893107b2202858c83a15840173 Mon Sep 17 00:00:00 2001 From: Christoph Kutzinski Date: Tue, 28 May 2013 14:13:48 +0200 Subject: [PATCH 143/233] Note changes for JENKINS-18086 --- changelog.html | 3 +++ 1 file changed, 3 insertions(+) diff --git a/changelog.html b/changelog.html index e18ef9fa66..72e7c0ac55 100644 --- a/changelog.html +++ b/changelog.html @@ -61,6 +61,9 @@ Upcoming changes
          • Allow filtering of the Run parameter build list by result. (issue 7280) +
          • + Add support for scalatest-maven-plugin. + (issue 18086)
          • When copying a folder, the display names of contained jobs were gratuitously cleared. (issue 18074) From 6fa54e93bdf4b43195298d638c9a292cb1e49253 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Tue, 28 May 2013 08:00:52 -0700 Subject: [PATCH 144/233] creating an RC branch --- changelog.html | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/changelog.html b/changelog.html index 72e7c0ac55..974f2c3c8f 100644 --- a/changelog.html +++ b/changelog.html @@ -54,6 +54,14 @@ Upcoming changes + + + - - -

            What's new in 1.516 (2013/05/27)

              From 1b4b557c264b2199dfa91849f13aeeb2ed377fb8 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Tue, 28 May 2013 08:00:57 -0700 Subject: [PATCH 145/233] the trunk is toward 1.518-SNAPSHOT --- cli/pom.xml | 2 +- core/pom.xml | 2 +- maven-plugin/pom.xml | 2 +- plugins/pom.xml | 12 ++++++------ pom.xml | 2 +- test/pom.xml | 2 +- ui-samples-plugin/pom.xml | 2 +- war/pom.xml | 2 +- 8 files changed, 13 insertions(+), 13 deletions(-) diff --git a/cli/pom.xml b/cli/pom.xml index 3df7ad60d5..766d450e7b 100644 --- a/cli/pom.xml +++ b/cli/pom.xml @@ -5,7 +5,7 @@ pom org.jenkins-ci.main - 1.517-SNAPSHOT + 1.518-SNAPSHOT cli diff --git a/core/pom.xml b/core/pom.xml index 0bd738476d..439073496b 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.517-SNAPSHOT + 1.518-SNAPSHOT ../pom.xml diff --git a/maven-plugin/pom.xml b/maven-plugin/pom.xml index bdc90e285c..bb41ae4fe7 100644 --- a/maven-plugin/pom.xml +++ b/maven-plugin/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.517-SNAPSHOT + 1.518-SNAPSHOT maven-plugin diff --git a/plugins/pom.xml b/plugins/pom.xml index 1826e1b805..2850cbf7ff 100644 --- a/plugins/pom.xml +++ b/plugins/pom.xml @@ -11,7 +11,7 @@ org.jenkins-ci.plugins plugin Jenkins plugin POM - 1.517-SNAPSHOT + 1.518-SNAPSHOT pom org.jenkins-ci.main maven-plugin - 1.517-SNAPSHOT + 1.518-SNAPSHOT @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.517-SNAPSHOT + 1.518-SNAPSHOT test org.jenkins-ci.main jenkins-core - 1.517-SNAPSHOT + 1.518-SNAPSHOT provided org.jenkins-ci.main jenkins-test-harness - 1.517-SNAPSHOT + 1.518-SNAPSHOT test org.jenkins-ci.main ui-samples-plugin - 1.517-SNAPSHOT + 1.518-SNAPSHOT test diff --git a/core/src/main/java/hudson/model/View.java b/core/src/main/java/hudson/model/View.java index 4f88290400..f394eb220b 100644 --- a/core/src/main/java/hudson/model/View.java +++ b/core/src/main/java/hudson/model/View.java @@ -792,7 +792,7 @@ public abstract class View extends AbstractModelObject implements AccessControll UserInfo info = users.get(user); if (info == null) { UserInfo userInfo = new UserInfo(user, p, build.getTimestamp()); - userInfo.avatar = UserAvatarResolver.resolve(user, iconSize); + userInfo.avatar = UserAvatarResolver.resolveOrNull(user, iconSize); synchronized (this) { users.put(user, userInfo); modified.add(user); @@ -824,7 +824,7 @@ public abstract class View extends AbstractModelObject implements AccessControll } if (!users.containsKey(u)) { UserInfo userInfo = new UserInfo(u, null, null); - userInfo.avatar = UserAvatarResolver.resolve(u, iconSize); + userInfo.avatar = UserAvatarResolver.resolveOrNull(u, iconSize); synchronized (this) { users.put(u, userInfo); modified.add(u); @@ -842,7 +842,7 @@ public abstract class View extends AbstractModelObject implements AccessControll accumulate("id", u.getId()). accumulate("fullName", u.getFullName()). accumulate("url", u.getUrl()). - accumulate("avatar", i.avatar). + accumulate("avatar", i.avatar != null ? i.avatar : Stapler.getCurrentRequest().getContextPath() + Functions.getResourcePath() + "/images/" + iconSize + "/user.png"). accumulate("timeSortKey", i.getTimeSortKey()). accumulate("lastChangeTimeString", i.getLastChangeTimeString()); AbstractProject p = i.getProject(); diff --git a/core/src/main/java/hudson/tasks/UserAvatarResolver.java b/core/src/main/java/hudson/tasks/UserAvatarResolver.java index 244a34a618..1cf8d13302 100644 --- a/core/src/main/java/hudson/tasks/UserAvatarResolver.java +++ b/core/src/main/java/hudson/tasks/UserAvatarResolver.java @@ -33,6 +33,7 @@ import hudson.ExtensionList; import hudson.ExtensionPoint; import hudson.Functions; import hudson.model.User; +import javax.annotation.CheckForNull; /** * Infers avatar image URLs for users @@ -78,13 +79,22 @@ public abstract class UserAvatarResolver implements ExtensionPoint { public abstract String findAvatarFor(User u, int width, int height); /** - * Resolve an avatar image URL string for the user + * Resolve an avatar image URL string for the user. + * Note that this method must be called from an HTTP request to be reliable; else use {@link #resolveOrNull}. * @param u user * @param avatarSize the preferred image size, "[width]x[height]" * @return a URL string for a user Avatar image. */ public static String resolve(User u, String avatarSize) { + String avatar = resolveOrNull(u, avatarSize); + return avatar != null ? avatar : Jenkins.getInstance().getRootUrl() + Functions.getResourcePath() + "/images/" + avatarSize + "/user.png"; + } + /** + * Like {@link #resolve} but returns null rather than a fallback URL in case there is no special avatar. + * @since 1.518 + */ + public static @CheckForNull String resolveOrNull(User u, String avatarSize) { Matcher matcher = iconSizeRegex.matcher(avatarSize); if (matcher.matches() && matcher.groupCount() == 2) { int width = Integer.parseInt(matcher.group(1)); @@ -97,7 +107,7 @@ public abstract class UserAvatarResolver implements ExtensionPoint { LOGGER.warning(String.format("Could not split up the avatar size (%s) into a width and height.", avatarSize)); } - return Jenkins.getInstance().getRootUrl() + Functions.getResourcePath() + "/images/" + avatarSize + "/user.png"; + return null; } /** From 315bde60d0618c0b17ffeab3f812adce3586c3da Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 28 May 2013 12:43:15 -0400 Subject: [PATCH 148/233] [FIXED JENKINS-18119] Work around timing issue in sortable object. Note that when workaround is active, table will not get sorted properly. Probably OK since tables with large contents that *need* sorting probably take longer to finish rendering. --- changelog.html | 3 +++ core/src/main/java/jenkins/util/ProgressiveRendering.java | 2 +- .../main/resources/hudson/model/View/AsynchPeople/index.jelly | 4 +++- 3 files changed, 7 insertions(+), 2 deletions(-) diff --git a/changelog.html b/changelog.html index 13b939e621..492aef617e 100644 --- a/changelog.html +++ b/changelog.html @@ -58,6 +58,9 @@ Upcoming changes
            • User icon in People broken if Jenkins root URL unconfigured. (issue 18118) +
            • + Progress bar sometimes broken in People. + (issue 18119)
            diff --git a/core/src/main/java/jenkins/util/ProgressiveRendering.java b/core/src/main/java/jenkins/util/ProgressiveRendering.java index 04b2f97956..d659d0b5ed 100644 --- a/core/src/main/java/jenkins/util/ProgressiveRendering.java +++ b/core/src/main/java/jenkins/util/ProgressiveRendering.java @@ -44,7 +44,7 @@ import org.kohsuke.stapler.bind.JavaScriptMethod; * (since it may be canceled if the user simply browses to another page while it is running). *
              *
            1. Write a {@code From 73706a45bce4bdce211f01a16bc8937f9c811bce Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 28 May 2013 13:20:55 -0400 Subject: [PATCH 149/233] [JENKINS-18074] Updated comment. --- core/src/main/java/hudson/model/DisplayNameListener.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/main/java/hudson/model/DisplayNameListener.java b/core/src/main/java/hudson/model/DisplayNameListener.java index 8a41ccf4a8..ed5cf71495 100644 --- a/core/src/main/java/hudson/model/DisplayNameListener.java +++ b/core/src/main/java/hudson/model/DisplayNameListener.java @@ -49,7 +49,7 @@ public class DisplayNameListener extends ItemListener { * displayed. */ public void onCopied(Item src, Item item) { - // bug 5056825 - Display name field should be cleared when you copy a job. + // bug 5056825 - Display name field should be cleared when you copy a job within the same folder. if(item instanceof AbstractItem && src.getParent() == item.getParent()) { AbstractItem dest = (AbstractItem)item; try { From 487a98afb62ef7170c30bbcb0db99a71bfec522d Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 28 May 2013 13:41:08 -0400 Subject: [PATCH 150/233] [JENKINS-18024] Noting. --- changelog.html | 3 +++ 1 file changed, 3 insertions(+) diff --git a/changelog.html b/changelog.html index 492aef617e..72280d3b03 100644 --- a/changelog.html +++ b/changelog.html @@ -55,6 +55,9 @@ Upcoming changes

              What's new in 1.516 (2013/05/27)

              • From 1f8d012b8d33ccc0eeeb283333b93cd9d514377c Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sun, 2 Jun 2013 20:32:50 -0700 Subject: [PATCH 174/233] updated changelog as a part of the release --- debian/debian/changelog | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/debian/debian/changelog b/debian/debian/changelog index 11a994920a..4efe4386c9 100644 --- a/debian/debian/changelog +++ b/debian/debian/changelog @@ -1,3 +1,9 @@ +jenkins (1.517) unstable; urgency=low + + * See http://jenkins-ci.org/changelog for more details. + + -- Kohsuke Kawaguchi Sun, 02 Jun 2013 19:14:40 -0700 + jenkins (1.516) unstable; urgency=low * See http://jenkins-ci.org/changelog for more details. From 3a4b1cb23deb6b63e92176806c2654252755d1aa Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sun, 2 Jun 2013 21:09:36 -0700 Subject: [PATCH 175/233] creating an RC branch --- changelog.html | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/changelog.html b/changelog.html index 786ee2758e..9b98708de3 100644 --- a/changelog.html +++ b/changelog.html @@ -54,6 +54,14 @@ Upcoming changes + + + - - -

                What's new in 1.517 (2013/06/02)

                  From 8eefed28c8b21557ee2281eca766ec72c4af4ea0 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sun, 2 Jun 2013 21:09:40 -0700 Subject: [PATCH 176/233] the trunk is toward 1.519-SNAPSHOT --- cli/pom.xml | 2 +- core/pom.xml | 2 +- maven-plugin/pom.xml | 2 +- plugins/pom.xml | 12 ++++++------ pom.xml | 2 +- test/pom.xml | 2 +- ui-samples-plugin/pom.xml | 2 +- war/pom.xml | 2 +- 8 files changed, 13 insertions(+), 13 deletions(-) diff --git a/cli/pom.xml b/cli/pom.xml index 766d450e7b..92983d2cc0 100644 --- a/cli/pom.xml +++ b/cli/pom.xml @@ -5,7 +5,7 @@ pom org.jenkins-ci.main - 1.518-SNAPSHOT + 1.519-SNAPSHOT cli diff --git a/core/pom.xml b/core/pom.xml index aee9a887c0..cc9bc5930d 100644 --- a/core/pom.xml +++ b/core/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.518-SNAPSHOT + 1.519-SNAPSHOT ../pom.xml diff --git a/maven-plugin/pom.xml b/maven-plugin/pom.xml index 2bf36fc43a..fae62bdbcb 100644 --- a/maven-plugin/pom.xml +++ b/maven-plugin/pom.xml @@ -29,7 +29,7 @@ THE SOFTWARE. org.jenkins-ci.main pom - 1.518-SNAPSHOT + 1.519-SNAPSHOT maven-plugin diff --git a/plugins/pom.xml b/plugins/pom.xml index 54c16e363f..20be1cc1f7 100644 --- a/plugins/pom.xml +++ b/plugins/pom.xml @@ -11,7 +11,7 @@ org.jenkins-ci.plugins plugin Jenkins plugin POM - 1.518-SNAPSHOT + 1.519-SNAPSHOT pom org.jenkins-ci.main maven-plugin - 1.518-SNAPSHOT + 1.519-SNAPSHOT @@ -48,25 +48,25 @@ org.jenkins-ci.main jenkins-war war - 1.518-SNAPSHOT + 1.519-SNAPSHOT test org.jenkins-ci.main jenkins-core - 1.518-SNAPSHOT + 1.519-SNAPSHOT provided org.jenkins-ci.main jenkins-test-harness - 1.518-SNAPSHOT + 1.519-SNAPSHOT test org.jenkins-ci.main ui-samples-plugin - 1.518-SNAPSHOT + 1.519-SNAPSHOT test From 5903870d318a337548e3f7ef75603f75a378e7ac Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Tue, 4 Jun 2013 20:19:35 -0400 Subject: [PATCH 184/233] [JENKINS-18065] Documenting current misbehavior in a unit test. --- .../lazy/AbstractLazyLoadRunMapTest.java | 42 +++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/core/src/test/java/jenkins/model/lazy/AbstractLazyLoadRunMapTest.java b/core/src/test/java/jenkins/model/lazy/AbstractLazyLoadRunMapTest.java index 9189e748bf..16bfcda069 100644 --- a/core/src/test/java/jenkins/model/lazy/AbstractLazyLoadRunMapTest.java +++ b/core/src/test/java/jenkins/model/lazy/AbstractLazyLoadRunMapTest.java @@ -30,11 +30,14 @@ import org.junit.Rule; import org.junit.Test; import java.io.IOException; +import java.util.Iterator; import java.util.Map; import java.util.NoSuchElementException; +import java.util.Set; import java.util.SortedMap; import java.util.logging.Level; import org.junit.BeforeClass; +import org.junit.Ignore; import org.jvnet.hudson.test.Bug; /** @@ -274,4 +277,43 @@ public class AbstractLazyLoadRunMapTest extends Assert { assertNull(map.search(3, Direction.DESC)); } + @Ignore("just calling entrySet triggers loading of every build!") + @Bug(18065) + @Test public void all() throws Exception { + assertEquals("[]", a.getLoadedBuilds().keySet().toString()); + Set> entries = a.entrySet(); + assertEquals("[]", a.getLoadedBuilds().keySet().toString()); + assertFalse(entries.isEmpty()); + assertEquals("[]", a.getLoadedBuilds().keySet().toString()); + assertEquals(5, a.getById("C").n); + assertEquals("[5]", a.getLoadedBuilds().keySet().toString()); + assertEquals("A", a.getByNumber(1).id); + assertEquals("[5, 1]", a.getLoadedBuilds().keySet().toString()); + a.purgeCache(); + assertEquals("[]", a.getLoadedBuilds().keySet().toString()); + Iterator> iterator = entries.iterator(); + assertEquals("[]", a.getLoadedBuilds().keySet().toString()); + assertTrue(iterator.hasNext()); + assertEquals("[]", a.getLoadedBuilds().keySet().toString()); + Map.Entry entry = iterator.next(); + assertEquals("[]", a.getLoadedBuilds().keySet().toString()); + assertEquals(5, entry.getKey().intValue()); + assertEquals("[]", a.getLoadedBuilds().keySet().toString()); + assertEquals("C", entry.getValue().id); + assertEquals("[5]", a.getLoadedBuilds().keySet().toString()); + assertTrue(iterator.hasNext()); + entry = iterator.next(); + assertEquals(3, entry.getKey().intValue()); + assertEquals("[5]", a.getLoadedBuilds().keySet().toString()); + assertEquals("B", entry.getValue().id); + assertEquals("[5, 3]", a.getLoadedBuilds().keySet().toString()); + assertTrue(iterator.hasNext()); + entry = iterator.next(); + assertEquals(1, entry.getKey().intValue()); + assertEquals("[5, 3]", a.getLoadedBuilds().keySet().toString()); + assertEquals("A", entry.getValue().id); + assertEquals("[5, 3, 1]", a.getLoadedBuilds().keySet().toString()); + assertFalse(iterator.hasNext()); + } + } From d964d0722039460ef9e0584b1b6b495c4094030c Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 5 Jun 2013 09:06:07 -0400 Subject: [PATCH 185/233] @since --- core/src/main/java/jenkins/util/JSONSignatureValidator.java | 1 + 1 file changed, 1 insertion(+) diff --git a/core/src/main/java/jenkins/util/JSONSignatureValidator.java b/core/src/main/java/jenkins/util/JSONSignatureValidator.java index 684f8ebe6c..77470f39ba 100644 --- a/core/src/main/java/jenkins/util/JSONSignatureValidator.java +++ b/core/src/main/java/jenkins/util/JSONSignatureValidator.java @@ -32,6 +32,7 @@ import java.util.logging.Logger; /** * @author Kohsuke Kawaguchi + * @since 1.482 */ public class JSONSignatureValidator { private final String name; From 291c39ad42dbd5e2676bc8229051f68f7b33ced5 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 5 Jun 2013 14:42:55 -0400 Subject: [PATCH 186/233] JUnit 4. --- .../java/hudson/tasks/FingerprinterTest.java | 73 ++++++++++--------- 1 file changed, 39 insertions(+), 34 deletions(-) diff --git a/test/src/test/java/hudson/tasks/FingerprinterTest.java b/test/src/test/java/hudson/tasks/FingerprinterTest.java index 5fcb24f312..ce5177afb3 100644 --- a/test/src/test/java/hudson/tasks/FingerprinterTest.java +++ b/test/src/test/java/hudson/tasks/FingerprinterTest.java @@ -38,15 +38,19 @@ import hudson.util.RunList; import java.io.IOException; import java.util.Collection; import java.util.List; +import static org.junit.Assert.*; +import org.junit.BeforeClass; +import org.junit.Rule; +import org.junit.Test; -import org.jvnet.hudson.test.HudsonTestCase; +import org.jvnet.hudson.test.JenkinsRule; /** * * @author dty */ @SuppressWarnings("rawtypes") -public class FingerprinterTest extends HudsonTestCase { +public class FingerprinterTest { private static final String[] singleContents = { "abcdef" }; @@ -71,18 +75,19 @@ public class FingerprinterTest extends HudsonTestCase { private static final String renamedProject1 = "renamed project 1"; private static final String renamedProject2 = "renamed project 2"; - @Override - public void setUp() throws Exception { - super.setUp(); + @Rule public JenkinsRule j = new JenkinsRule(); + + @BeforeClass + public static void setUp() throws Exception { Fingerprinter.enableFingerprintsInDependencyGraph = true; } - public void testFingerprintDependencies() throws Exception { + @Test public void fingerprintDependencies() throws Exception { FreeStyleProject upstream = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); FreeStyleProject downstream = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); - assertBuildStatusSuccess(upstream.scheduleBuild2(0).get()); - assertBuildStatusSuccess(downstream.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(upstream.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(downstream.scheduleBuild2(0).get()); List downstreamProjects = upstream.getDownstreamProjects(); List upstreamProjects = downstream.getUpstreamProjects(); @@ -93,14 +98,14 @@ public class FingerprinterTest extends HudsonTestCase { assertTrue(downstreamProjects.contains(downstream)); } - public void testMultipleUpstreamDependencies() throws Exception { + @Test public void multipleUpstreamDependencies() throws Exception { FreeStyleProject upstream = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); FreeStyleProject upstream2 = createFreeStyleProjectWithFingerprints(singleContents2, singleFiles2); FreeStyleProject downstream = createFreeStyleProjectWithFingerprints(doubleContents, doubleFiles); - assertBuildStatusSuccess(upstream.scheduleBuild2(0).get()); - assertBuildStatusSuccess(upstream2.scheduleBuild2(0).get()); - assertBuildStatusSuccess(downstream.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(upstream.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(upstream2.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(downstream.scheduleBuild2(0).get()); List downstreamProjects = upstream.getDownstreamProjects(); List downstreamProjects2 = upstream2.getDownstreamProjects(); @@ -114,14 +119,14 @@ public class FingerprinterTest extends HudsonTestCase { assertTrue(downstreamProjects.contains(downstream)); } - public void testMultipleDownstreamDependencies() throws Exception { + @Test public void multipleDownstreamDependencies() throws Exception { FreeStyleProject upstream = createFreeStyleProjectWithFingerprints(doubleContents, doubleFiles); FreeStyleProject downstream = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); FreeStyleProject downstream2 = createFreeStyleProjectWithFingerprints(singleContents2, singleFiles2); - assertBuildStatusSuccess(upstream.scheduleBuild2(0).get()); - assertBuildStatusSuccess(downstream.scheduleBuild2(0).get()); - assertBuildStatusSuccess(downstream2.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(upstream.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(downstream.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(downstream2.scheduleBuild2(0).get()); List downstreamProjects = upstream.getDownstreamProjects(); List upstreamProjects = downstream.getUpstreamProjects(); @@ -136,12 +141,12 @@ public class FingerprinterTest extends HudsonTestCase { assertTrue(downstreamProjects.contains(downstream2)); } - public void testDependencyExclusion() throws Exception { + @Test public void dependencyExclusion() throws Exception { FreeStyleProject upstream = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); FreeStyleProject downstream = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); - FreeStyleBuild upstreamBuild = assertBuildStatusSuccess(upstream.scheduleBuild2(0).get()); - assertBuildStatusSuccess(downstream.scheduleBuild2(0).get()); + FreeStyleBuild upstreamBuild = j.assertBuildStatusSuccess(upstream.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(downstream.scheduleBuild2(0).get()); upstreamBuild.delete(); @@ -154,11 +159,11 @@ public class FingerprinterTest extends HudsonTestCase { assertEquals(0, downstreamProjects.size()); } - public void testCircularDependency() throws Exception { + @Test public void circularDependency() throws Exception { FreeStyleProject p = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); - assertBuildStatusSuccess(p.scheduleBuild2(0).get()); - assertBuildStatusSuccess(p.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(p.scheduleBuild2(0).get()); + j.assertBuildStatusSuccess(p.scheduleBuild2(0).get()); List upstreamProjects = p.getUpstreamProjects(); List downstreamProjects = p.getDownstreamProjects(); @@ -167,34 +172,34 @@ public class FingerprinterTest extends HudsonTestCase { assertEquals(0, downstreamProjects.size()); } - public void testMatrixDependency() throws Exception { - MatrixProject matrixProject = createMatrixProject(); + @Test public void MatrixDependency() throws Exception { + MatrixProject matrixProject = j.createMatrixProject(); matrixProject.setAxes(new AxisList(new Axis("foo", "a", "b"))); FreeStyleProject freestyleProject = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); addFingerprinterToProject(matrixProject, singleContents, singleFiles); - jenkins.rebuildDependencyGraph(); + j.jenkins.rebuildDependencyGraph(); - buildAndAssertSuccess(matrixProject); - buildAndAssertSuccess(freestyleProject); - waitUntilNoActivity(); + j.buildAndAssertSuccess(matrixProject); + j.buildAndAssertSuccess(freestyleProject); + j.waitUntilNoActivity(); RunList builds = freestyleProject.getBuilds(); assertEquals("There should only be one FreestyleBuild", 1, builds.size()); FreeStyleBuild build = builds.iterator().next(); assertEquals(Result.SUCCESS, build.getResult()); - List downstream = jenkins.getDependencyGraph().getDownstream(matrixProject); + List downstream = j.jenkins.getDependencyGraph().getDownstream(matrixProject); assertTrue(downstream.contains(freestyleProject)); - List upstream = jenkins.getDependencyGraph().getUpstream(freestyleProject); + List upstream = j.jenkins.getDependencyGraph().getUpstream(freestyleProject); assertTrue(upstream.contains(matrixProject)); } - public void testProjectRename() throws Exception { + @Test public void projectRename() throws Exception { FreeStyleProject upstream = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); FreeStyleProject downstream = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); - FreeStyleBuild upstreamBuild = assertBuildStatusSuccess(upstream.scheduleBuild2(0).get()); - FreeStyleBuild downstreamBuild = assertBuildStatusSuccess(downstream.scheduleBuild2(0).get()); + FreeStyleBuild upstreamBuild = j.assertBuildStatusSuccess(upstream.scheduleBuild2(0).get()); + FreeStyleBuild downstreamBuild = j.assertBuildStatusSuccess(downstream.scheduleBuild2(0).get()); String oldUpstreamName = upstream.getName(); String oldDownstreamName = downstream.getName(); @@ -246,7 +251,7 @@ public class FingerprinterTest extends HudsonTestCase { } private FreeStyleProject createFreeStyleProjectWithFingerprints(String[] contents, String[] files) throws IOException, Exception { - FreeStyleProject project = createFreeStyleProject(); + FreeStyleProject project = j.createFreeStyleProject(); addFingerprinterToProject(project, contents, files); From bd709b0631329f1abaf05de4a3499562a1606691 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 5 Jun 2013 15:06:29 -0400 Subject: [PATCH 187/233] [JENKINS-17125] Establishing baseline FingerprintAction behavior that should not be regressed. --- .../java/hudson/tasks/FingerprinterTest.java | 24 ++++++++++++++++++ .../FingerprinterTest/actionSerialization.zip | Bin 0 -> 2904 bytes 2 files changed, 24 insertions(+) create mode 100644 test/src/test/resources/hudson/tasks/FingerprinterTest/actionSerialization.zip diff --git a/test/src/test/java/hudson/tasks/FingerprinterTest.java b/test/src/test/java/hudson/tasks/FingerprinterTest.java index ce5177afb3..2c7a8b9179 100644 --- a/test/src/test/java/hudson/tasks/FingerprinterTest.java +++ b/test/src/test/java/hudson/tasks/FingerprinterTest.java @@ -24,6 +24,7 @@ package hudson.tasks; +import hudson.XmlFile; import hudson.matrix.Axis; import hudson.matrix.AxisList; import hudson.matrix.MatrixProject; @@ -34,6 +35,7 @@ import hudson.model.FreeStyleProject; import hudson.model.Hudson; import hudson.model.Result; import hudson.util.RunList; +import java.io.File; import java.io.IOException; import java.util.Collection; @@ -44,6 +46,7 @@ import org.junit.Rule; import org.junit.Test; import org.jvnet.hudson.test.JenkinsRule; +import org.jvnet.hudson.test.recipes.LocalData; /** * @@ -249,6 +252,27 @@ public class FingerprinterTest { assertFalse(jobs.contains(oldDownstreamName)); } } + + @LocalData + @Test public void actionSerialization() throws Exception { + FreeStyleProject job = j.jenkins.getItemByFullName("j", FreeStyleProject.class); + assertNotNull(job); + FreeStyleBuild build = job.getBuildByNumber(2); + assertNotNull(build); + Fingerprinter.FingerprintAction action = build.getAction(Fingerprinter.FingerprintAction.class); + assertNotNull(action); + assertEquals(build, action.getBuild()); + assertEquals("{a=2d5fac981a2e865baf0e15db655c7d63}", action.getRecords().toString()); + j.assertBuildStatusSuccess(job.scheduleBuild2(0)); + job._getRuns().purgeCache(); // force build records to be reloaded + build = job.getBuildByNumber(3); + assertNotNull(build); + System.out.println(new XmlFile(new File(build.getRootDir(), "build.xml")).asString()); + action = build.getAction(Fingerprinter.FingerprintAction.class); + assertNotNull(action); + assertEquals(build, action.getBuild()); + assertEquals("{a=f31efcf9afe30617d6c46b919e702822}", action.getRecords().toString()); + } private FreeStyleProject createFreeStyleProjectWithFingerprints(String[] contents, String[] files) throws IOException, Exception { FreeStyleProject project = j.createFreeStyleProject(); diff --git a/test/src/test/resources/hudson/tasks/FingerprinterTest/actionSerialization.zip b/test/src/test/resources/hudson/tasks/FingerprinterTest/actionSerialization.zip new file mode 100644 index 0000000000000000000000000000000000000000..b56ba95facbd72008542b7dad70a607f205563b2 GIT binary patch literal 2904 zcmWIWW@Zs#U|`^2I9hzv>6rA+M^hLX7#=b+FbFcpFl6N?73*i|C+Fv-Wv1&@e%gYxU%rv;2Ue-MtZnzMfA;mL*faZ}y*m0&0z_EXDwX{8622~Bb+zky z$AXw*^%MVi%-jBSme?rlke!!YmVCTl)#Ij6Z$_x$)a3`fWo3QDubXdvzWj}rmCl{W zBYUb&Z+H5*LFnr>%^5SQR9kiHSI)oKbp1<{(UYYM%C~Pmw5`Q=8b`6PPwpW`nJTCsU9m z`!Ox)4UWyfWgt@fJlti^2HPWk37iI!;i6gFy`rNvH(Wn;W4b^=Qi}E4U+>eUnR3>y z^7ObswdB#5=n} z9_O~3tuzw}xlyTnq?ZbY5ZAI5~wl8xz80KqzOw~Ln@BivnR9YF^ zU8`>kzVFJ?d9nNl)4#)dYeWlA_RRds{K8%8+Jd=k2CtP{4zI6ITiU3ttM{$(*sJTt zWpc@PmrOEh>c3`vaN&t-J^t#N(uY*ehvm$5nAI6NFSSPJ)5Y6SP5)=Pd{CV{+2;R# z`-9@sReYn@J6u*g=)PKfhf%J0D6ffZ?_~X(7M|^w1E1|IZH$|6WXq*XNtW~Pi?phX zZQ$<=+iYMU>(61QDE~-$8E=Hty&2Zu1b>u`;UHa zcl~lQ^T!#TBc6SedH5%nh^U^tZqmQ+Z_JU~L18uDckXt*uB>tL^}DIE{7-FO?3-G& zFY%p4-d^|p`|b9a9EyJF7I|5;Fm!Ry${?nqw70KzP7>PTYX0@!zI#_ovw``0;TG1w zhOf1JQk=io5os2b3-}*PB(nh%EePuqm9COA67$kibMg^IASioaNn18RHTrg_$=K3& z--29VGClyrszg}_Gz6YYuvlU{(K~;!fk^B3Kdm`?X2_nJVbX6kb<+VARU5S>s_&F9 z>KwRmLuEz}FUyaws-f2Dh3_w3y?9am?uMR}nQ97oj!T0$+1RISesSD{g?X}WnqX-&|MyYqjoySnhTP>#{Q?H@nN zr@u+bIdmp^Us?XgAC{KCXSBTER_#<)`O;%A?_pK9Z(F|XIMDa@P3hGi@3`LW4&8h2 ztopj+*82??N#=RXyUBP{x_*~v%#+jFm?BsZ$Rue@&Udh>5blL`zz zd5A1J+wGOPsS&q6n}Hq zF-jCOiZUNw_Fm&NcS`6Yu12-XKkqmkyCKp4uJ>Y&)$g@4mNie=#8h*gZ}Y>sXykgxfT_a!_ z&d4OkjH}w00Qrsqm|7XOG=f-I8Ud`3MgWFCK*r*#Zjg<=4>TQWEJo!6G#eC7c+AGE zcpzpoFbFXGbuOaH6Jr%Dv4;X(Mkt|xN_*7ogzU8z dlI#O!E?gF}f@%_A3z~z$7uZz!3N)610RYms^;iG^ literal 0 HcmV?d00001 From dfe2b9a21a94d22c43e923f8ad2c6e75ee9bfe1a Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 5 Jun 2013 15:51:33 -0400 Subject: [PATCH 188/233] Fixing casing of test method. --- test/src/test/java/hudson/tasks/FingerprinterTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/src/test/java/hudson/tasks/FingerprinterTest.java b/test/src/test/java/hudson/tasks/FingerprinterTest.java index 2c7a8b9179..1ab5537380 100644 --- a/test/src/test/java/hudson/tasks/FingerprinterTest.java +++ b/test/src/test/java/hudson/tasks/FingerprinterTest.java @@ -175,7 +175,7 @@ public class FingerprinterTest { assertEquals(0, downstreamProjects.size()); } - @Test public void MatrixDependency() throws Exception { + @Test public void matrixDependency() throws Exception { MatrixProject matrixProject = j.createMatrixProject(); matrixProject.setAxes(new AxisList(new Axis("foo", "a", "b"))); FreeStyleProject freestyleProject = createFreeStyleProjectWithFingerprints(singleContents, singleFiles); From a614cd5b05b3c8cbcb8970ea439b2a1315252f58 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 5 Jun 2013 16:02:36 -0400 Subject: [PATCH 189/233] [FIXED JENKINS-17125] FingerprintAction no longer need persist the build field thanks to new RunAction2. --- changelog.html | 3 ++ .../main/java/hudson/model/CauseAction.java | 11 ++--- core/src/main/java/hudson/model/Run.java | 16 +++++-- .../src/main/java/hudson/model/RunAction.java | 7 +-- .../main/java/hudson/tasks/Fingerprinter.java | 42 +++++++---------- .../main/java/jenkins/model/RunAction2.java | 46 +++++++++++++++++++ .../FingerprintAction/index.jelly | 4 +- 7 files changed, 87 insertions(+), 42 deletions(-) create mode 100644 core/src/main/java/jenkins/model/RunAction2.java diff --git a/changelog.html b/changelog.html index 7d0064d778..61f1a6c68a 100644 --- a/changelog.html +++ b/changelog.html @@ -58,6 +58,9 @@ Upcoming changes
                • Log cluttered with irrelevant warnings about build timestamps when running on Windows on Java 6. (issue 15587) +
                • + Fingerprint action deserialization problem fixed. + (issue 17125)
                diff --git a/core/src/main/java/hudson/model/CauseAction.java b/core/src/main/java/hudson/model/CauseAction.java index e29dfeed57..c3a967932b 100644 --- a/core/src/main/java/hudson/model/CauseAction.java +++ b/core/src/main/java/hudson/model/CauseAction.java @@ -35,9 +35,10 @@ import java.util.ArrayList; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; +import jenkins.model.RunAction2; @ExportedBean -public class CauseAction implements FoldableAction, RunAction { +public class CauseAction implements FoldableAction, RunAction2 { /** * @deprecated since 2009-02-28 */ @@ -105,18 +106,14 @@ public class CauseAction implements FoldableAction, RunAction { return causes.get(0).getShortDescription(); } - public void onLoad() { - // noop - } - - public void onBuildComplete() { + @Override public void onLoad(Run r) { // noop } /** * When hooked up to build, notify {@link Cause}s. */ - public void onAttached(Run owner) { + @Override public void onAttached(Run owner) { if (owner instanceof AbstractBuild) {// this should be always true but being defensive here AbstractBuild b = (AbstractBuild) owner; for (Cause c : causes) { diff --git a/core/src/main/java/hudson/model/Run.java b/core/src/main/java/hudson/model/Run.java index c0d026261f..474738068b 100644 --- a/core/src/main/java/hudson/model/Run.java +++ b/core/src/main/java/hudson/model/Run.java @@ -120,6 +120,7 @@ import java.io.OutputStream; import static java.util.logging.Level.*; import javax.annotation.CheckForNull; import javax.annotation.Nonnull; +import jenkins.model.RunAction2; /** * A particular execution of {@link Job}. @@ -314,10 +315,15 @@ public abstract class Run ,RunT extends Run,RunT extends Run record) { this.build = build; this.record = PackedMap.of(record); - onLoad(); // make compact + compact(); } public void add(Map moreRecords) { @@ -316,7 +316,7 @@ public class Fingerprinter extends Recorder implements Serializable, DependencyD r.putAll(moreRecords); record = PackedMap.of(r); ref = null; - onLoad(); + compact(); } public String getIconFileName() { @@ -342,15 +342,16 @@ public class Fingerprinter extends Recorder implements Serializable, DependencyD return record; } - public void onLoad() { - if (build == null) { - return; - } - if (build.getParent() == null) { - logger.warning("JENKINS-16845: broken FingerprintAction record"); - build = null; - return; - } + @Override public void onLoad(Run r) { + build = (AbstractBuild) r; + compact(); + } + + @Override public void onAttached(Run r) { + // for historical reasons this setup is done in the constructor instead + } + + private void compact() { // share data structure with nearby builds, but to keep lazy loading efficient, // don't go back the history forever. if (rand.nextInt(2)!=0) { @@ -363,12 +364,6 @@ public class Fingerprinter extends Recorder implements Serializable, DependencyD } } - public void onAttached(Run r) { - } - - public void onBuildComplete() { - } - /** * Reuse string instances from another {@link FingerprintAction} to reduce memory footprint. */ @@ -438,11 +433,6 @@ public class Fingerprinter extends Recorder implements Serializable, DependencyD public Map getDependencies(boolean includeMissing) { Map r = new HashMap(); - if (build == null) { - // Broken, do not do anything. - return r; - } - for (Fingerprint fp : getFingerprints().values()) { BuildPtr bp = fp.getOriginal(); if(bp==null) continue; // outside Hudson diff --git a/core/src/main/java/jenkins/model/RunAction2.java b/core/src/main/java/jenkins/model/RunAction2.java new file mode 100644 index 0000000000..d655042a4f --- /dev/null +++ b/core/src/main/java/jenkins/model/RunAction2.java @@ -0,0 +1,46 @@ +/* + * The MIT License + * + * Copyright 2013 Jesse Glick. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +package jenkins.model; + +import hudson.model.Action; +import hudson.model.Run; + +/** + * Optional interface for {@link Action}s that add themselves to a {@link Run}. + * @since 1.519 + */ +public interface RunAction2 extends Action { + + /** + * Called when this action is {@linkplain Run#addAction added to a build}. + */ + void onAttached(Run r); + + /** + * Called after a {@linkplain Run#onLoad build is loaded} to which this action was previously {@linkplain #onAttached attached}. + */ + void onLoad(Run r); + +} diff --git a/core/src/main/resources/hudson/tasks/Fingerprinter/FingerprintAction/index.jelly b/core/src/main/resources/hudson/tasks/Fingerprinter/FingerprintAction/index.jelly index d0b191a5a9..3f9230984f 100644 --- a/core/src/main/resources/hudson/tasks/Fingerprinter/FingerprintAction/index.jelly +++ b/core/src/main/resources/hudson/tasks/Fingerprinter/FingerprintAction/index.jelly @@ -30,9 +30,7 @@ THE SOFTWARE. - - - +

                From 2c23e643fac3efef98eec03b83adf735f07a2d62 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Wed, 5 Jun 2013 16:04:21 -0400 Subject: [PATCH 190/233] @Bug --- test/src/test/java/hudson/tasks/FingerprinterTest.java | 2 ++ 1 file changed, 2 insertions(+) diff --git a/test/src/test/java/hudson/tasks/FingerprinterTest.java b/test/src/test/java/hudson/tasks/FingerprinterTest.java index 1ab5537380..d2f0b2eb23 100644 --- a/test/src/test/java/hudson/tasks/FingerprinterTest.java +++ b/test/src/test/java/hudson/tasks/FingerprinterTest.java @@ -44,6 +44,7 @@ import static org.junit.Assert.*; import org.junit.BeforeClass; import org.junit.Rule; import org.junit.Test; +import org.jvnet.hudson.test.Bug; import org.jvnet.hudson.test.JenkinsRule; import org.jvnet.hudson.test.recipes.LocalData; @@ -253,6 +254,7 @@ public class FingerprinterTest { } } + @Bug(17125) @LocalData @Test public void actionSerialization() throws Exception { FreeStyleProject job = j.jenkins.getItemByFullName("j", FreeStyleProject.class); From effcc2d7aa4f40a3f43185ab0bc22619d6ecea97 Mon Sep 17 00:00:00 2001 From: Nicolas De Loof Date: Thu, 6 Jun 2013 11:32:27 +0200 Subject: [PATCH 191/233] offer better pronouns for common job types --- core/src/main/java/hudson/matrix/MatrixProject.java | 6 ++++++ core/src/main/resources/hudson/matrix/Messages.properties | 1 + core/src/main/resources/hudson/model/Messages.properties | 2 +- .../src/main/java/hudson/maven/MavenModuleSet.java | 7 +++++++ .../src/main/resources/hudson/maven/Messages.properties | 1 + 5 files changed, 16 insertions(+), 1 deletion(-) diff --git a/core/src/main/java/hudson/matrix/MatrixProject.java b/core/src/main/java/hudson/matrix/MatrixProject.java index 8598974d47..7dae077835 100644 --- a/core/src/main/java/hudson/matrix/MatrixProject.java +++ b/core/src/main/java/hudson/matrix/MatrixProject.java @@ -41,6 +41,7 @@ import hudson.model.Descriptor; import hudson.model.Descriptor.FormException; import hudson.model.Node; import hudson.slaves.WorkspaceList; +import hudson.util.AlternativeUiTextProvider; import jenkins.model.Jenkins; import hudson.model.Item; import hudson.model.ItemGroup; @@ -194,6 +195,11 @@ public class MatrixProject extends AbstractProject im super(parent, name); } + @Override + public String getPronoun() { + return AlternativeUiTextProvider.get(PRONOUN, this, Messages.MatrixProject_Pronoun()); + } + /** * Gets the workspace location that {@link MatrixConfiguration} uses. * diff --git a/core/src/main/resources/hudson/matrix/Messages.properties b/core/src/main/resources/hudson/matrix/Messages.properties index 8536028184..325ece3185 100644 --- a/core/src/main/resources/hudson/matrix/Messages.properties +++ b/core/src/main/resources/hudson/matrix/Messages.properties @@ -22,6 +22,7 @@ MatrixBuild.depends_on_this={0} depends on this. MatrixProject.DisplayName=Build multi-configuration project +MatrixProject.Pronoun=Multi-configuration project MatrixProject.DuplicateAxisName=Duplicate axis name MatrixBuild.Triggering=Triggering {0} diff --git a/core/src/main/resources/hudson/model/Messages.properties b/core/src/main/resources/hudson/model/Messages.properties index 97ac72ca57..6f5df4cbde 100644 --- a/core/src/main/resources/hudson/model/Messages.properties +++ b/core/src/main/resources/hudson/model/Messages.properties @@ -119,7 +119,7 @@ Descriptor.From=(from {0}) Executor.NotAvailable=N/A ExternalJob.DisplayName=Monitor an external job -ExternalJob.Pronoun=Job +ExternalJob.Pronoun=External Job FreeStyleProject.DisplayName=Build a free-style software project diff --git a/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java b/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java index 90b0097265..a870b32837 100644 --- a/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java @@ -67,6 +67,7 @@ import hudson.tasks.Maven.MavenInstallation; import hudson.tasks.Publisher; import hudson.tasks.JavadocArchiver; import hudson.tasks.junit.JUnitResultArchiver; +import hudson.util.AlternativeUiTextProvider; import hudson.util.CopyOnWriteMap; import hudson.util.DescribableList; import hudson.util.FormValidation; @@ -446,6 +447,12 @@ public class MavenModuleSet extends AbstractMavenProject Date: Thu, 6 Jun 2013 10:10:30 -0400 Subject: [PATCH 192/233] [FIXED JENKINS-18236] Noting retroactively. --- changelog.html | 3 +++ 1 file changed, 3 insertions(+) diff --git a/changelog.html b/changelog.html index 61f1a6c68a..1d34749c3d 100644 --- a/changelog.html +++ b/changelog.html @@ -273,6 +273,9 @@ Upcoming changes
              • Improved UI for implicitly locked builds. (issue 10197) +
              • + Incorrect URL computation broke context menu for computers with spaces in their names. + (issue 18236)
              • Promote the use of 'H' in cron. (issue 17311) From 951f927aa99bd280391970238b85de1b42142dc8 Mon Sep 17 00:00:00 2001 From: ddavison Date: Thu, 6 Jun 2013 14:12:45 -0400 Subject: [PATCH 193/233] Taking out the `defaulted` js logic with the search-box, and embracing CSS3's 'placeholder' attribute. Prettying up the search box --- .../main/resources/lib/layout/layout.jelly | 4 ++-- war/src/main/webapp/css/style.css | 8 ++++---- .../main/webapp/scripts/hudson-behavior.js | 19 ------------------- 3 files changed, 6 insertions(+), 25 deletions(-) diff --git a/core/src/main/resources/lib/layout/layout.jelly b/core/src/main/resources/lib/layout/layout.jelly index e9a053ea48..b7449b8376 100644 --- a/core/src/main/resources/lib/layout/layout.jelly +++ b/core/src/main/resources/lib/layout/layout.jelly @@ -45,7 +45,7 @@ THE SOFTWARE. This was originally added to allow plugins to load their stylesheets, but *the use of thie attribute is discouraged now.* - plugins should now do so by inserting <style> elements and/or <script> elements + plugins should now do so by inserting <style> elements and/or <script> elementsg in <l:header/> tag. @@ -170,7 +170,7 @@ ${h.initPageVariables(context)}
                - + help for search
                diff --git a/war/src/main/webapp/css/style.css b/war/src/main/webapp/css/style.css index a1975e01b9..b1ee9cca0f 100644 --- a/war/src/main/webapp/css/style.css +++ b/war/src/main/webapp/css/style.css @@ -894,10 +894,10 @@ DIV.yahooTree td { padding-left: 20px; width: 15em; position: static; -} - -#search-box.defaulted { - color: gray; + border: 1px solid #DDD; + border-radius: 4px; + box-shadow: 0 0 5px #DDD inset; + outline: none; } #search-box-completion { diff --git a/war/src/main/webapp/scripts/hudson-behavior.js b/war/src/main/webapp/scripts/hudson-behavior.js index 18309bdb9c..d9dfd3deb2 100644 --- a/war/src/main/webapp/scripts/hudson-behavior.js +++ b/war/src/main/webapp/scripts/hudson-behavior.js @@ -607,25 +607,6 @@ var jenkinsRules = { e = null; // avoid memory leak }, -// scripting for having default value in the input field - "INPUT.has-default-text" : function(e) { - var defaultValue = e.value; - Element.addClassName(e, "defaulted"); - e.onfocus = function() { - if (this.value == defaultValue) { - this.value = ""; - Element.removeClassName(this, "defaulted"); - } - } - e.onblur = function() { - if (this.value == "") { - this.value = defaultValue; - Element.addClassName(this, "defaulted"); - } - } - e = null; // avoid memory leak - }, - //
              • Fingerprint action deserialization problem fixed. (issue 17125) +
              • + Improved the tracking of queued jobs and their eventual builds in the REST API.
              diff --git a/core/src/main/java/hudson/model/AbstractProject.java b/core/src/main/java/hudson/model/AbstractProject.java index 239d6ffaed..14571c3503 100644 --- a/core/src/main/java/hudson/model/AbstractProject.java +++ b/core/src/main/java/hudson/model/AbstractProject.java @@ -1798,8 +1798,11 @@ public abstract class AbstractProject

              ,R extends A if (!isBuildable()) throw HttpResponses.error(SC_INTERNAL_SERVER_ERROR,new IOException(getFullName()+" is not buildable")); - Jenkins.getInstance().getQueue().schedule(this, (int)delay.getTime(), getBuildCause(req)); - rsp.sendRedirect("."); + WaitingItem item = Jenkins.getInstance().getQueue().schedule(this, (int) delay.getTime(), getBuildCause(req)); + if (item!=null) { + rsp.sendRedirect(SC_CREATED,req.getContextPath()+'/'+item.getUrl()); + } else + rsp.sendRedirect("."); } /** diff --git a/core/src/main/java/hudson/model/Executor.java b/core/src/main/java/hudson/model/Executor.java index 4fcb0968fd..b99b6fbb02 100644 --- a/core/src/main/java/hudson/model/Executor.java +++ b/core/src/main/java/hudson/model/Executor.java @@ -214,6 +214,7 @@ public class Executor extends Thread implements ModelObject { task = workUnit.work; startTime = System.currentTimeMillis(); executable = task.createExecutable(); + workUnit.setExecutable(executable); } if (LOGGER.isLoggable(FINE)) LOGGER.log(FINE, getName()+" is going to execute "+executable); diff --git a/core/src/main/java/hudson/model/ParametersDefinitionProperty.java b/core/src/main/java/hudson/model/ParametersDefinitionProperty.java index 0cc266ce43..e25116bb6f 100644 --- a/core/src/main/java/hudson/model/ParametersDefinitionProperty.java +++ b/core/src/main/java/hudson/model/ParametersDefinitionProperty.java @@ -34,6 +34,7 @@ import java.util.AbstractList; import javax.servlet.ServletException; +import hudson.model.Queue.WaitingItem; import jenkins.model.Jenkins; import jenkins.util.TimeDuration; import net.sf.json.JSONArray; @@ -48,6 +49,8 @@ import org.kohsuke.stapler.export.ExportedBean; import hudson.Extension; import org.kohsuke.stapler.export.Flavor; +import static javax.servlet.http.HttpServletResponse.SC_CREATED; + /** * Keeps a list of the parameters defined for a project. * @@ -132,11 +135,13 @@ public class ParametersDefinitionProperty extends JobProperty * This class implements the core scheduling logic. {@link Task} represents the executable * task that are placed in the queue. While in the queue, it's wrapped into {@link Item} - * so that we can keep track of additional data used for deciding what to exeucte when. + * so that we can keep track of additional data used for deciding what to execute when. * *

              * Items in queue goes through several stages, as depicted below: @@ -125,7 +132,7 @@ import org.kohsuke.stapler.interceptor.RequirePOST; * | ^ * | | * | v - * +--> buildables ---> pending ---> (executed) + * +--> buildables ---> pending ---> left * * *

              @@ -167,8 +174,36 @@ public class Queue extends ResourceController implements Saveable { */ private final ItemList pendings = new ItemList(); + /** + * Items that left queue would stay here for a while to enable tracking via {@link Item#id}. + * + * This map is forgetful, since we can't remember everything that executed in the past. + */ +// private final FifoMap leftItems = new FifoMap(256); + private final Cache leftItems = CacheBuilder.newBuilder().expireAfterWrite(5*60, TimeUnit.SECONDS).build(); + private final CachedItemList itemsView = new CachedItemList(); +// class FifoMap { +// private final ConcurrentMap store = new ConcurrentHashMap(); +// private final BlockingQueue order = new LinkedBlockingQueue(); +// private final int size; +// +// FifoMap(int size) { +// this.size = size; +// } +// +// private void add(K k, V v) { +// store.put(k,v); +// order.add(k); +// while (order.size()>size) +// store.remove(order.remove()); +// } +// +// public V get(K k) { +// return store.get(k); +// } +// } /** * Maintains a copy of {@link Queue#getItems()} * @@ -612,6 +647,10 @@ public class Queue extends ResourceController implements Saveable { LOGGER.log(Level.FINE, "Cancelling {0} item#{1}", new Object[] {item.task, item.id}); // use bitwise-OR to make sure that all the branches get evaluated all the time boolean r = (item instanceof WaitingItem && waitingList.remove(item)) | blockedProjects.remove(item) | buildables.remove(item); + + LeftItem li = new LeftItem(item); + leftItems.put(li.id,li); + if(r) item.onCancelled(); return r; @@ -683,7 +722,8 @@ public class Queue extends ResourceController implements Saveable { for (Item item: blockedProjects) if (item.id == id) return item; for (Item item: buildables) if (item.id == id) return item; for (Item item: pendings) if (item.id == id) return item; - return null; + + return leftItems.getIfPresent(id); } /** @@ -720,6 +760,13 @@ public class Queue extends ResourceController implements Saveable { return new ArrayList(pendings.values()); } + /** + * Returns the snapshot of all {@link LeftItem}s. + */ + public Collection getLeftItems() { + return Collections.unmodifiableCollection(leftItems.asMap().values()); + } + /** * Gets all items that are in the queue but not blocked * @@ -852,6 +899,9 @@ public class Queue extends ResourceController implements Saveable { OneOffExecutor ooe = (OneOffExecutor) exec; final WorkUnit wu = ooe.getAssignedWorkUnit(); pendings.remove(wu.context.item); + + LeftItem li = new LeftItem(wu.context); + leftItems.put(li.id,li); return wu; } @@ -895,8 +945,11 @@ public class Queue extends ResourceController implements Saveable { LOGGER.log(Level.FINE, "Pop returning {0} for {1}", new Object[] {offer.workUnit, exec.getName()}); // TODO: I think this has to be done by the last executor that leaves the pop(), not by main executor - if (offer.workUnit.isMainWork()) + if (offer.workUnit.isMainWork()) { pendings.remove(offer.workUnit.context.item); + LeftItem li = new LeftItem(offer.workUnit.context); + leftItems.put(li.id,li); + } return offer.workUnit; } @@ -1407,6 +1460,17 @@ public class Queue extends ResourceController implements Saveable { this(item.task, item.getActions(), item.id, item.future, item.inQueueSince); } + /** + * Returns the URL of this {@link Item} relative to the context path of Jenkins + * + * @return + * URL that ends with '/'. + */ + @Exported + public String getUrl() { + return "queue/item/"+id+'/'; + } + /** * Gets a human-readable status message describing why it's in the queue. */ @@ -1468,6 +1532,10 @@ public class Queue extends ResourceController implements Saveable { future.setAsCancelled(); } + public Api getApi() { + return new Api(this); + } + private Object readResolve() { this.future = new FutureImpl(task); return this; @@ -1691,6 +1759,52 @@ public class Queue extends ResourceController implements Saveable { } } + /** + * {@link Item} in the {@link Queue#leftItems} stage. These are items that had left the queue + * by either began executing or by getting cancelled. + */ + public final static class LeftItem extends Item { + public final WorkUnitContext outcome; + + /** + * When item has left the queue and begin executing. + */ + public LeftItem(WorkUnitContext wuc) { + super(wuc.item); + this.outcome = wuc; + } + + /** + * When item is cancelled. + */ + public LeftItem(Item cancelled) { + super(cancelled); + this.outcome = null; + } + + @Override + public CauseOfBlockage getCauseOfBlockage() { + return null; + } + + /** + * If this is representing an item that started executing, this property returns + * the primary executable (such as {@link AbstractBuild}) that created out of it. + */ + @Exported + public Executable getExecutable() { + return outcome!=null ? outcome.getPrimaryWorkUnit().getExecutable() : null; + } + + /** + * Is this representing a cancelled item? + */ + @Exported + public boolean isCancelled() { + return outcome==null; + } + } + private static final Logger LOGGER = Logger.getLogger(Queue.class.getName()); /** diff --git a/core/src/main/java/hudson/model/queue/WorkUnit.java b/core/src/main/java/hudson/model/queue/WorkUnit.java index 739cdfe64a..000bc02ee6 100644 --- a/core/src/main/java/hudson/model/queue/WorkUnit.java +++ b/core/src/main/java/hudson/model/queue/WorkUnit.java @@ -48,6 +48,7 @@ public final class WorkUnit { public final WorkUnitContext context; private volatile Executor executor; + private Executable executable; WorkUnit(WorkUnitContext context, SubTask work) { this.context = context; @@ -69,10 +70,14 @@ public final class WorkUnit { } /** - * If the execution has already started, return the current executable. + * If the execution has already started, return the executable that was created. */ public Executable getExecutable() { - return executor!=null ? executor.getCurrentExecutable() : null; + return executable; + } + + public void setExecutable(Executable executable) { + this.executable = executable; } /** diff --git a/core/src/main/resources/hudson/model/Job/_api.jelly b/core/src/main/resources/hudson/model/Job/_api.jelly index 5d019fbb39..4d73d50d62 100644 --- a/core/src/main/resources/hudson/model/Job/_api.jelly +++ b/core/src/main/resources/hudson/model/Job/_api.jelly @@ -37,6 +37,11 @@ THE SOFTWARE.

              To programmatically schedule a new build, post to this URL. If the build has parameters, post to this URL and provide the parameters as form data. + Either way, the successful queueing will result in 201 status code with Location HTTP header + pointing the URL of the item in the queue. By polling the api/xml sub-URL of the queue item, + you can track the status of the queued task. Generally, the task will go through some state transitions, + then eventually it becomes either cancelled (look for the "cancelled" boolean property), or gets executed + (look for the "executable" property that typically points to the AbstractBuild object.)

              To programmatically schedule SCM polling, post to this URL. From 6a3743a526fccc6474c9d8aa0b1c38a3b0981285 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Fri, 7 Jun 2013 19:52:10 +0300 Subject: [PATCH 208/233] deleted this earlier experiment --- core/src/main/java/hudson/model/Queue.java | 21 --------------------- 1 file changed, 21 deletions(-) diff --git a/core/src/main/java/hudson/model/Queue.java b/core/src/main/java/hudson/model/Queue.java index 5d24715143..7fdb4369b2 100644 --- a/core/src/main/java/hudson/model/Queue.java +++ b/core/src/main/java/hudson/model/Queue.java @@ -179,31 +179,10 @@ public class Queue extends ResourceController implements Saveable { * * This map is forgetful, since we can't remember everything that executed in the past. */ -// private final FifoMap leftItems = new FifoMap(256); private final Cache leftItems = CacheBuilder.newBuilder().expireAfterWrite(5*60, TimeUnit.SECONDS).build(); private final CachedItemList itemsView = new CachedItemList(); -// class FifoMap { -// private final ConcurrentMap store = new ConcurrentHashMap(); -// private final BlockingQueue order = new LinkedBlockingQueue(); -// private final int size; -// -// FifoMap(int size) { -// this.size = size; -// } -// -// private void add(K k, V v) { -// store.put(k,v); -// order.add(k); -// while (order.size()>size) -// store.remove(order.remove()); -// } -// -// public V get(K k) { -// return store.get(k); -// } -// } /** * Maintains a copy of {@link Queue#getItems()} * From b1f5d28f90ca1dc99de775bb2bed46ada48e68f4 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Fri, 7 Jun 2013 20:02:49 +0300 Subject: [PATCH 209/233] doc improvements based on Jesse's comments --- changelog.html | 2 ++ core/src/main/java/hudson/model/Queue.java | 5 +++++ core/src/main/java/hudson/model/queue/WorkUnit.java | 6 ++++++ .../main/java/hudson/maven/AbstractMavenProcessFactory.java | 1 + .../src/main/java/hudson/maven/MavenEmbedderRequest.java | 1 + 5 files changed, 15 insertions(+) diff --git a/changelog.html b/changelog.html index a2d1ff1577..b62d249949 100644 --- a/changelog.html +++ b/changelog.html @@ -63,6 +63,8 @@ Upcoming changes (issue 17125)

            2. Improved the tracking of queued jobs and their eventual builds in the REST API. +
            3. + Added a new extension point to contribute custom plexus components into Maven for the maven project type.
          diff --git a/core/src/main/java/hudson/model/Queue.java b/core/src/main/java/hudson/model/Queue.java index 7fdb4369b2..e53da67dc2 100644 --- a/core/src/main/java/hudson/model/Queue.java +++ b/core/src/main/java/hudson/model/Queue.java @@ -741,6 +741,8 @@ public class Queue extends ResourceController implements Saveable { /** * Returns the snapshot of all {@link LeftItem}s. + * + * @since 1.519 */ public Collection getLeftItems() { return Collections.unmodifiableCollection(leftItems.asMap().values()); @@ -1444,6 +1446,7 @@ public class Queue extends ResourceController implements Saveable { * * @return * URL that ends with '/'. + * @since 1.519 */ @Exported public String getUrl() { @@ -1741,6 +1744,8 @@ public class Queue extends ResourceController implements Saveable { /** * {@link Item} in the {@link Queue#leftItems} stage. These are items that had left the queue * by either began executing or by getting cancelled. + * + * @since 1.519 */ public final static class LeftItem extends Item { public final WorkUnitContext outcome; diff --git a/core/src/main/java/hudson/model/queue/WorkUnit.java b/core/src/main/java/hudson/model/queue/WorkUnit.java index 000bc02ee6..c9ffb3e8d6 100644 --- a/core/src/main/java/hudson/model/queue/WorkUnit.java +++ b/core/src/main/java/hudson/model/queue/WorkUnit.java @@ -27,6 +27,8 @@ import hudson.model.Executor; import hudson.model.Queue; import hudson.model.Queue.Executable; import hudson.model.Queue.Task; +import org.kohsuke.accmod.Restricted; +import org.kohsuke.accmod.restrictions.NoExternalUse; import org.kohsuke.stapler.export.ExportedBean; /** @@ -76,6 +78,10 @@ public final class WorkUnit { return executable; } + /** + * This method is only meant to be called internally by {@link Executor}. + */ + @Restricted(NoExternalUse.class) public void setExecutable(Executable executable) { this.executable = executable; } diff --git a/maven-plugin/src/main/java/hudson/maven/AbstractMavenProcessFactory.java b/maven-plugin/src/main/java/hudson/maven/AbstractMavenProcessFactory.java index 9ea895c7e1..8e7e9d9094 100644 --- a/maven-plugin/src/main/java/hudson/maven/AbstractMavenProcessFactory.java +++ b/maven-plugin/src/main/java/hudson/maven/AbstractMavenProcessFactory.java @@ -260,6 +260,7 @@ public abstract class AbstractMavenProcessFactory /** * Apply extension plexus modules to the newly launched Maven process. + * @since 1.519 */ protected abstract void applyPlexusModuleContributor(Channel channel) throws InterruptedException, IOException; diff --git a/maven-plugin/src/main/java/hudson/maven/MavenEmbedderRequest.java b/maven-plugin/src/main/java/hudson/maven/MavenEmbedderRequest.java index 975d860670..b4720e0417 100755 --- a/maven-plugin/src/main/java/hudson/maven/MavenEmbedderRequest.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenEmbedderRequest.java @@ -192,6 +192,7 @@ public class MavenEmbedderRequest /** * Default value of {@link #getClassLoader()} + * @since 1.519 */ public static ClassLoader getDefaultMavenClassLoader() { return new MaskingClassLoader( MavenUtil.class.getClassLoader() ); From ad60e8e867689220d6b72ac67fabaa655812c04c Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Fri, 7 Jun 2013 20:10:29 +0300 Subject: [PATCH 210/233] doc improvements and shortening variable names in the hope of making it bit more readable --- .../hudson/maven/MavenEmbedderRequest.java | 5 ++ .../java/hudson/maven/MavenModuleSet.java | 2 + .../hudson/maven/MavenModuleSetBuild.java | 28 +++++------ .../src/main/java/hudson/maven/MavenUtil.java | 46 +++++++++---------- 4 files changed, 45 insertions(+), 36 deletions(-) diff --git a/maven-plugin/src/main/java/hudson/maven/MavenEmbedderRequest.java b/maven-plugin/src/main/java/hudson/maven/MavenEmbedderRequest.java index b4720e0417..73784b4a3e 100755 --- a/maven-plugin/src/main/java/hudson/maven/MavenEmbedderRequest.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenEmbedderRequest.java @@ -229,6 +229,11 @@ public class MavenEmbedderRequest return validationLevel; } + /** + * Controls the level of error checks done while parsing POM. + * + * @see ModelBuildingRequest#VALIDATION_LEVEL_MAVEN_3_0 + */ public MavenEmbedderRequest setValidationLevel( int validationLevel ) { this.validationLevel = validationLevel; return this; diff --git a/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java b/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java index a870b32837..24039aefab 100644 --- a/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenModuleSet.java @@ -248,7 +248,9 @@ public class MavenModuleSet extends AbstractMavenProject(), new File(workspaceProper) ); - mavenEmbedderRequest.setWorkspaceReader( reactorReader ); + mer.setWorkspaceReader(reactorReader); } {// create a classloader that loads extensions List urls = plexusContributors.getPlexusComponentJars(); if (!urls.isEmpty()) { - mavenEmbedderRequest.setClassLoader( - new URLClassLoader(urls.toArray(new URL[urls.size()]), - mavenEmbedderRequest.getClassLoader())); + mer.setClassLoader( + new URLClassLoader(urls.toArray(new URL[urls.size()]), + mer.getClassLoader())); } } if (this.mavenValidationLevel >= 0) { - mavenEmbedderRequest.setValidationLevel( this.mavenValidationLevel ); + mer.setValidationLevel(this.mavenValidationLevel); } //mavenEmbedderRequest.setClassLoader( MavenEmbedderUtils.buildClassRealm( mavenHome.getHomeDir(), null, null ) ); - MavenEmbedder embedder = MavenUtil.createEmbedder( mavenEmbedderRequest ); + MavenEmbedder embedder = MavenUtil.createEmbedder( mer ); MavenProject rootProject = null; diff --git a/maven-plugin/src/main/java/hudson/maven/MavenUtil.java b/maven-plugin/src/main/java/hudson/maven/MavenUtil.java index 0ff693b542..7c5d6e2355 100755 --- a/maven-plugin/src/main/java/hudson/maven/MavenUtil.java +++ b/maven-plugin/src/main/java/hudson/maven/MavenUtil.java @@ -144,7 +144,7 @@ public class MavenUtil { * */ @SuppressWarnings("RV_RETURN_VALUE_IGNORED_BAD_PRACTICE") - public static MavenEmbedder createEmbedder(MavenEmbedderRequest mavenEmbedderRequest) throws MavenEmbedderException, IOException { + public static MavenEmbedder createEmbedder(MavenEmbedderRequest mer) throws MavenEmbedderException, IOException { MavenRequest mavenRequest = new MavenRequest(); @@ -155,48 +155,48 @@ public class MavenUtil { if(!m2Home.exists()) throw new AbortException("Failed to create "+m2Home); - if (mavenEmbedderRequest.getPrivateRepository()!=null) - mavenRequest.setLocalRepositoryPath( mavenEmbedderRequest.getPrivateRepository() ); + if (mer.getPrivateRepository()!=null) + mavenRequest.setLocalRepositoryPath( mer.getPrivateRepository() ); - if (mavenEmbedderRequest.getProfiles() != null) { - mavenRequest.setProfiles(Arrays.asList( StringUtils.split( mavenEmbedderRequest.getProfiles(), "," ) )); + if (mer.getProfiles() != null) { + mavenRequest.setProfiles(Arrays.asList( StringUtils.split( mer.getProfiles(), "," ) )); } - if ( mavenEmbedderRequest.getAlternateSettings() != null ) { - mavenRequest.setUserSettingsFile( mavenEmbedderRequest.getAlternateSettings().getAbsolutePath() ); + if ( mer.getAlternateSettings() != null ) { + mavenRequest.setUserSettingsFile( mer.getAlternateSettings().getAbsolutePath() ); } else { mavenRequest.setUserSettingsFile( new File( m2Home, "settings.xml" ).getAbsolutePath() ); } - if ( mavenEmbedderRequest.getGlobalSettings() != null) { - mavenRequest.setGlobalSettingsFile( mavenEmbedderRequest.getGlobalSettings().getAbsolutePath() ); + if ( mer.getGlobalSettings() != null) { + mavenRequest.setGlobalSettingsFile( mer.getGlobalSettings().getAbsolutePath() ); } else { - mavenRequest.setGlobalSettingsFile( new File( mavenEmbedderRequest.getMavenHome(), "conf/settings.xml" ).getAbsolutePath() ); + mavenRequest.setGlobalSettingsFile( new File( mer.getMavenHome(), "conf/settings.xml" ).getAbsolutePath() ); } - if (mavenEmbedderRequest.getWorkspaceReader() != null ) { - mavenRequest.setWorkspaceReader( mavenEmbedderRequest.getWorkspaceReader() ); + if (mer.getWorkspaceReader() != null ) { + mavenRequest.setWorkspaceReader( mer.getWorkspaceReader() ); } - mavenRequest.setUpdateSnapshots(mavenEmbedderRequest.isUpdateSnapshots()); + mavenRequest.setUpdateSnapshots(mer.isUpdateSnapshots()); // TODO olamy check this sould be userProperties - mavenRequest.setSystemProperties(mavenEmbedderRequest.getSystemProperties()); + mavenRequest.setSystemProperties(mer.getSystemProperties()); - if (mavenEmbedderRequest.getTransferListener() != null) { + if (mer.getTransferListener() != null) { if (debugMavenEmbedder) { - mavenEmbedderRequest.getListener().getLogger() - .println( "use transfertListener " + mavenEmbedderRequest.getTransferListener().getClass().getName() ); + mer.getListener().getLogger() + .println( "use transfertListener " + mer.getTransferListener().getClass().getName() ); } - mavenRequest.setTransferListener( mavenEmbedderRequest.getTransferListener() ); + mavenRequest.setTransferListener( mer.getTransferListener() ); } EmbedderLoggerImpl logger = - new EmbedderLoggerImpl( mavenEmbedderRequest.getListener(), debugMavenEmbedder ? org.codehaus.plexus.logging.Logger.LEVEL_DEBUG + new EmbedderLoggerImpl( mer.getListener(), debugMavenEmbedder ? org.codehaus.plexus.logging.Logger.LEVEL_DEBUG : org.codehaus.plexus.logging.Logger.LEVEL_INFO ); mavenRequest.setMavenLoggerManager( logger ); - ClassLoader mavenEmbedderClassLoader = mavenEmbedderRequest.getClassLoader(); + ClassLoader mavenEmbedderClassLoader = mer.getClassLoader(); {// are we loading the right components.xml? (and not from Maven that's running Jetty, if we are running in "mvn hudson-dev:run" or "mvn hpi:run"? Enumeration e = mavenEmbedderClassLoader.getResources("META-INF/plexus/components.xml"); @@ -206,9 +206,9 @@ public class MavenUtil { } } - mavenRequest.setProcessPlugins( mavenEmbedderRequest.isProcessPlugins() ); - mavenRequest.setResolveDependencies( mavenEmbedderRequest.isResolveDependencies() ); - mavenRequest.setValidationLevel( mavenEmbedderRequest.getValidationLevel() ); + mavenRequest.setProcessPlugins( mer.isProcessPlugins() ); + mavenRequest.setResolveDependencies( mer.isResolveDependencies() ); + mavenRequest.setValidationLevel( mer.getValidationLevel() ); // TODO check this MaskingClassLoader with maven 3 artifacts MavenEmbedder maven = new MavenEmbedder( mavenEmbedderClassLoader, mavenRequest ); From f7330d7a158eff6705706b1f812993a9b918c351 Mon Sep 17 00:00:00 2001 From: Kohsuke Kawaguchi Date: Sat, 8 Jun 2013 12:21:18 +0300 Subject: [PATCH 211/233] [FIXED JENKINS-15120] - integrated the newer release of remoting - jar caching won't work with class file directory, so plugin WEB-INF/classes are now exploded as WEB-INF/lib/classes.jar (This should also solve the problem of slow plugin extraction in the presene of Anti-virus software on Windows.) - because the structure of the exploded jar file has changed, I changed the up-to-date check timestamp file name to force re-extraction in existing installations. --- changelog.html | 3 + .../java/hudson/ClassicPluginStrategy.java | 86 ++++++++++++++++--- .../main/java/hudson/maven/Maven3Builder.java | 5 ++ pom.xml | 2 +- 4 files changed, 84 insertions(+), 12 deletions(-) diff --git a/changelog.html b/changelog.html index b62d249949..062b8e4bde 100644 --- a/changelog.html +++ b/changelog.html @@ -65,6 +65,9 @@ Upcoming changes Improved the tracking of queued jobs and their eventual builds in the REST API.
        • Added a new extension point to contribute custom plexus components into Maven for the maven project type. +
        • + Remoting classloader performance improvement upon reconnection to the same slave. + (issue 15120)
        diff --git a/core/src/main/java/hudson/ClassicPluginStrategy.java b/core/src/main/java/hudson/ClassicPluginStrategy.java index 56b8ee5990..28c1ad78e5 100644 --- a/core/src/main/java/hudson/ClassicPluginStrategy.java +++ b/core/src/main/java/hudson/ClassicPluginStrategy.java @@ -23,7 +23,6 @@ */ package hudson; -import com.google.common.collect.Iterables; import com.google.common.collect.Lists; import hudson.Plugin.DummyImpl; import hudson.PluginWrapper.Dependency; @@ -36,11 +35,21 @@ import hudson.util.MaskingClassLoader; import hudson.util.VersionNumber; import jenkins.ClassLoaderReflectionToolkit; import jenkins.ExtensionFilter; +import org.apache.commons.io.output.NullOutputStream; import org.apache.tools.ant.AntClassLoader; import org.apache.tools.ant.BuildException; import org.apache.tools.ant.Project; import org.apache.tools.ant.taskdefs.Expand; +import org.apache.tools.ant.taskdefs.Zip; import org.apache.tools.ant.types.FileSet; +import org.apache.tools.ant.types.PatternSet; +import org.apache.tools.ant.types.Resource; +import org.apache.tools.ant.types.ZipFileSet; +import org.apache.tools.ant.types.resources.MappedResourceCollection; +import org.apache.tools.ant.util.GlobPatternMapper; +import org.apache.tools.zip.ZipEntry; +import org.apache.tools.zip.ZipExtraField; +import org.apache.tools.zip.ZipOutputStream; import java.io.Closeable; import java.io.File; @@ -57,7 +66,6 @@ import java.util.Collection; import java.util.Collections; import java.util.Enumeration; import java.util.HashSet; -import java.util.Iterator; import java.util.List; import java.util.Vector; import java.util.jar.Attributes; @@ -413,11 +421,10 @@ public class ClassicPluginStrategy implements PluginStrategy { * Explodes the plugin into a directory, if necessary. */ private static void explode(File archive, File destDir) throws IOException { - if(!destDir.exists()) - destDir.mkdirs(); + destDir.mkdirs(); // timestamp check - File explodeTime = new File(destDir,".timestamp"); + File explodeTime = new File(destDir,".timestamp2"); if(explodeTime.exists() && explodeTime.lastModified()==archive.lastModified()) return; // no need to expand @@ -425,12 +432,9 @@ public class ClassicPluginStrategy implements PluginStrategy { Util.deleteRecursive(destDir); try { - Expand e = new Expand(); - e.setProject(new Project()); - e.setTaskType("unzip"); - e.setSrc(archive); - e.setDest(destDir); - e.execute(); + Project prj = new Project(); + unzipExceptClasses(archive, destDir, prj); + createClassJarFromWebInfClasses(archive, destDir, prj); } catch (BuildException x) { throw new IOException2("Failed to expand " + archive,x); } @@ -442,6 +446,66 @@ public class ClassicPluginStrategy implements PluginStrategy { } } + /** + * Repackage classes directory into a jar file to make it remoting friendly. + * The remoting layer can cache jar files but not class files. + */ + private static void createClassJarFromWebInfClasses(File archive, File destDir, Project prj) { + File classesJar = new File(destDir, "WEB-INF/lib/classes.jar"); + + ZipFileSet zfs = new ZipFileSet(); + zfs.setProject(prj); + zfs.setSrc(archive); + zfs.setIncludes("WEB-INF/classes/"); + + MappedResourceCollection mapper = new MappedResourceCollection(); + mapper.add(zfs); + + GlobPatternMapper gm = new GlobPatternMapper(); + gm.setFrom("WEB-INF/classes/*"); + gm.setTo("*"); + mapper.add(gm); + + final long dirTime = archive.lastModified(); + Zip z = new Zip() { + /** + * Forces the fixed timestamp for directories to make sure + * classes.jar always get a consistent checksum. + */ + protected void zipDir(Resource dir, ZipOutputStream zOut, String vPath, + int mode, ZipExtraField[] extra) + throws IOException { + + ZipOutputStream wrapped = new ZipOutputStream(new NullOutputStream()) { + @Override + public void putNextEntry(ZipEntry ze) throws IOException { + ze.setTime(dirTime+1999); // roundup + super.putNextEntry(ze); + } + }; + super.zipDir(dir,wrapped,vPath,mode,extra); + } + }; + z.setProject(prj); + z.setTaskType("zip"); + classesJar.getParentFile().mkdirs(); + z.setDestFile(classesJar); + z.add(mapper); + z.execute(); + } + + private static void unzipExceptClasses(File archive, File destDir, Project prj) { + Expand e = new Expand(); + e.setProject(prj); + e.setTaskType("unzip"); + e.setSrc(archive); + e.setDest(destDir); + PatternSet p = new PatternSet(); + p.setExcludes("WEB-INF/classes/"); + e.addPatternset(p); + e.execute(); + } + /** * Used to load classes from dependency plugins. */ diff --git a/maven-plugin/src/main/java/hudson/maven/Maven3Builder.java b/maven-plugin/src/main/java/hudson/maven/Maven3Builder.java index 50010b4130..d39e3f603b 100644 --- a/maven-plugin/src/main/java/hudson/maven/Maven3Builder.java +++ b/maven-plugin/src/main/java/hudson/maven/Maven3Builder.java @@ -160,6 +160,9 @@ public class Maven3Builder extends AbstractMavenBuilder implements DelegatingCal throw new IOException2(e); } catch (Exception e) { throw new IOException2(e); + } finally { + if (DUMP_PERFORMANCE_COUNTERS) + Channel.current().dumpPerformanceCounters(listener.error("Remoting stats")); } } @@ -571,4 +574,6 @@ public class Maven3Builder extends AbstractMavenBuilder implements DelegatingCal private static final long serialVersionUID = 1L; private static final Logger LOGGER = Logger.getLogger(Maven3Builder.class.getName()); + + public static boolean DUMP_PERFORMANCE_COUNTERS = Boolean.getBoolean(Maven3Builder.class.getName()+".dumpPerformanceCounters"); } diff --git a/pom.xml b/pom.xml index 39b2808075..b071d7747e 100644 --- a/pom.xml +++ b/pom.xml @@ -175,7 +175,7 @@ THE SOFTWARE. org.jenkins-ci.main remoting - 2.23 + 2.24 From cabbe941c73a0db63e59492ff2e3722c41b239f0 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Mon, 10 Jun 2013 09:18:04 -0400 Subject: [PATCH 212/233] fixed @since --- core/src/main/java/hudson/slaves/SlaveComputer.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/main/java/hudson/slaves/SlaveComputer.java b/core/src/main/java/hudson/slaves/SlaveComputer.java index 97a2578f44..dab036eecb 100644 --- a/core/src/main/java/hudson/slaves/SlaveComputer.java +++ b/core/src/main/java/hudson/slaves/SlaveComputer.java @@ -351,7 +351,7 @@ public class SlaveComputer extends Computer { /** * Shows {@link Channel#classLoadingPrefetchCacheCount}. * @return -1 in case that capability is not supported - * @since XXX prefetch-JENKINS-15120 + * @since 1.519 */ public int getClassLoadingPrefetchCacheCount() throws IOException, InterruptedException { if (!channel.remoteCapability.supportsPrefetch()) { From aec064adc5f4d1cbef77c909276695301b17900c Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Mon, 10 Jun 2013 10:44:32 -0400 Subject: [PATCH 213/233] Make assertGC more useful by showing root references in case of failure. --- .../main/java/org/jvnet/hudson/test/MemoryAssert.java | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/test/src/main/java/org/jvnet/hudson/test/MemoryAssert.java b/test/src/main/java/org/jvnet/hudson/test/MemoryAssert.java index 054b20a6fe..360bf159c9 100644 --- a/test/src/main/java/org/jvnet/hudson/test/MemoryAssert.java +++ b/test/src/main/java/org/jvnet/hudson/test/MemoryAssert.java @@ -24,6 +24,7 @@ package org.jvnet.hudson.test; +import edu.umd.cs.findbugs.annotations.SuppressWarnings; import java.lang.ref.WeakReference; import java.util.ArrayList; import java.util.Collections; @@ -33,6 +34,7 @@ import java.util.Set; import java.util.concurrent.Callable; import jenkins.model.Jenkins; import static org.junit.Assert.*; +import org.netbeans.insane.live.LiveReferences; import org.netbeans.insane.scanner.CountingVisitor; import org.netbeans.insane.scanner.Filter; import org.netbeans.insane.scanner.ScannerUtils; @@ -133,6 +135,7 @@ public class MemoryAssert { * Forces GC by causing an OOM and then verifies the given {@link WeakReference} has been garbage collected. * @param reference object used to verify garbage collection. */ + @SuppressWarnings("DLS_DEAD_LOCAL_STORE_OF_NULL") public static void assertGC(WeakReference reference) { assertTrue(true); reference.get(); // preload any needed classes! Set objects = new HashSet(); @@ -143,7 +146,12 @@ public class MemoryAssert { break; } } - assertTrue(reference.get() == null); + objects = null; + System.gc(); + Object obj = reference.get(); + if (obj != null) { + fail(LiveReferences.fromRoots(Collections.singleton(obj)).toString()); + } } } From e67746c97ff91c391d058b9beb592618cfd1f614 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Mon, 10 Jun 2013 10:52:16 -0400 Subject: [PATCH 214/233] Queue.clearLeftItems to fix AbstractProjectTest.testGetBuildAfterGC test failure after 84a2593. --- core/src/main/java/hudson/model/Queue.java | 13 +++++++++---- .../test/java/hudson/model/AbstractProjectTest.java | 1 + 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/core/src/main/java/hudson/model/Queue.java b/core/src/main/java/hudson/model/Queue.java index e53da67dc2..a162856f59 100644 --- a/core/src/main/java/hudson/model/Queue.java +++ b/core/src/main/java/hudson/model/Queue.java @@ -92,10 +92,6 @@ import java.util.Set; import java.util.Timer; import java.util.TreeSet; import java.util.Map.Entry; -import java.util.concurrent.BlockingQueue; -import java.util.concurrent.ConcurrentHashMap; -import java.util.concurrent.ConcurrentMap; -import java.util.concurrent.LinkedBlockingQueue; import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.Future; @@ -748,6 +744,15 @@ public class Queue extends ResourceController implements Saveable { return Collections.unmodifiableCollection(leftItems.asMap().values()); } + /** + * Immediately clear the {@link #getLeftItems} cache. + * Useful for tests which need to verify that no links to a build remain. + * @since 1.519 + */ + public void clearLeftItems() { + leftItems.invalidateAll(); + } + /** * Gets all items that are in the queue but not blocked * diff --git a/test/src/test/java/hudson/model/AbstractProjectTest.java b/test/src/test/java/hudson/model/AbstractProjectTest.java index f9c01f3318..754211e15c 100644 --- a/test/src/test/java/hudson/model/AbstractProjectTest.java +++ b/test/src/test/java/hudson/model/AbstractProjectTest.java @@ -291,6 +291,7 @@ public class AbstractProjectTest extends HudsonTestCase { public void testGetBuildAfterGC() throws Exception { FreeStyleProject job = createFreeStyleProject(); job.scheduleBuild2(0, new Cause.UserIdCause()).get(); + jenkins.getQueue().clearLeftItems(); MemoryAssert.assertGC(new WeakReference(job.getLastBuild())); assertTrue(job.getLastBuild() != null); } From b1c82f1e30fa5f6483415f2c7ad1b95aed1eb072 Mon Sep 17 00:00:00 2001 From: Jesse Glick Date: Mon, 10 Jun 2013 11:53:13 -0400 Subject: [PATCH 215/233] stephenc asks to use TODO rather than XXX --- core/src/main/java/hudson/FilePath.java | 2 +- core/src/main/java/hudson/PluginManager.java | 2 +- core/src/main/java/hudson/Util.java | 4 ++-- core/src/main/java/hudson/model/Fingerprint.java | 2 +- core/src/main/java/hudson/model/JDK.java | 2 +- core/src/main/java/hudson/model/Run.java | 4 ++-- .../java/hudson/model/StreamBuildListener.java | 2 +- core/src/main/java/hudson/model/View.java | 4 ++-- .../main/java/hudson/tasks/junit/JUnitParser.java | 2 +- .../main/java/hudson/tools/CommandInstaller.java | 2 +- .../main/java/hudson/util/FormFieldValidator.java | 2 +- core/src/main/java/hudson/util/FormValidation.java | 2 +- core/src/main/java/hudson/util/XStream2.java | 2 +- core/src/main/java/jenkins/model/Jenkins.java | 14 +++++++------- .../model/lazy/BuildReferenceMapAdapter.java | 4 ++-- .../main/resources/hudson/AboutJenkins/index.jelly | 2 +- .../hudson/slaves/JNLPLauncher/main.jelly | 2 +- .../hudson/tasks/BuildTrigger/config.jelly | 2 +- .../hudson/tools/JDKInstaller/config.jelly | 2 +- core/src/main/resources/hudson/tools/label.jelly | 2 +- .../resources/jenkins/model/Jenkins/manage.jelly | 2 +- core/src/main/resources/lib/hudson/queue.jelly | 2 +- core/src/main/resources/lib/layout/breadcrumbs.js | 2 +- .../lib/layout/progressiveRendering.jelly | 2 +- .../progressiveRendering/progressiveRendering.js | 2 +- core/src/test/java/hudson/FilePathTest.java | 2 +- core/src/test/java/hudson/FunctionsTest.java | 2 +- .../resources/hudson/maven/Messages.properties | 2 +- .../hudson/maven/Messages_zh_TW.properties | 2 +- .../java/org/jvnet/hudson/test/JenkinsRule.java | 2 +- .../java/org/jvnet/hudson/test/MemoryAssert.java | 2 +- .../java/org/jvnet/hudson/test/MockFolder.java | 2 +- test/src/test/java/hudson/PluginManagerTest.java | 6 +++--- .../test/java/hudson/cli/CopyJobCommandTest.java | 2 +- .../hudson/init/impl/GroovyInitScriptTest.java | 2 +- .../java/hudson/model/AbstractProjectTest.java | 2 +- .../java/hudson/tasks/junit/SuiteResultTest.java | 2 +- war/src/main/webapp/scripts/hudson-behavior.js | 6 +++--- 38 files changed, 52 insertions(+), 52 deletions(-) diff --git a/core/src/main/java/hudson/FilePath.java b/core/src/main/java/hudson/FilePath.java index cee15b41a7..ecd2b97ce5 100644 --- a/core/src/main/java/hudson/FilePath.java +++ b/core/src/main/java/hudson/FilePath.java @@ -497,7 +497,7 @@ public final class FilePath implements Serializable { private static void unzip(File dir, InputStream in) throws IOException { File tmpFile = File.createTempFile("tmpzip", null); // uses java.io.tmpdir try { - // XXX why does this not simply use ZipInputStream? + // TODO why does this not simply use ZipInputStream? IOUtils.copy(in, tmpFile); unzip(dir,tmpFile); } diff --git a/core/src/main/java/hudson/PluginManager.java b/core/src/main/java/hudson/PluginManager.java index b2aa0e59da..8bdb17ae89 100644 --- a/core/src/main/java/hudson/PluginManager.java +++ b/core/src/main/java/hudson/PluginManager.java @@ -797,7 +797,7 @@ public abstract class PluginManager extends AbstractModelObject implements OnMas Jenkins.getInstance().checkPermission(Jenkins.ADMINISTER); List> jobs = new ArrayList>(); UpdateCenter uc = Jenkins.getInstance().getUpdateCenter(); - // XXX call uc.updateAllSites() when available? perhaps not, since we should not block on network here + // TODO call uc.updateAllSites() when available? perhaps not, since we should not block on network here for (Map.Entry requestedPlugin : parseRequestedPlugins(configXml).entrySet()) { PluginWrapper pw = getPlugin(requestedPlugin.getKey()); if (pw == null) { // install new diff --git a/core/src/main/java/hudson/Util.java b/core/src/main/java/hudson/Util.java index d91b85fa75..47ad0bc665 100644 --- a/core/src/main/java/hudson/Util.java +++ b/core/src/main/java/hudson/Util.java @@ -1075,14 +1075,14 @@ public class Util { // we still prefer to try JNA first as PosixAPI supports even smaller platforms. POSIX posix = PosixAPI.jnr(); if (posix.isNative()) { - // XXX should we rethrow PosixException as IOException here? + // TODO should we rethrow PosixException as IOException here? r = posix.symlink(targetPath,symlinkFile.getAbsolutePath()); } } } if (r==null) { // if all else fail, fall back to the most expensive approach of forking a process - // XXX is this really necessary? JavaPOSIX should do this automatically + // TODO is this really necessary? JavaPOSIX should do this automatically r = new LocalProc(new String[]{ "ln","-s", targetPath, symlinkPath}, new String[0],listener.getLogger(), baseDir).join(); diff --git a/core/src/main/java/hudson/model/Fingerprint.java b/core/src/main/java/hudson/model/Fingerprint.java index e30143f452..c1b40239aa 100644 --- a/core/src/main/java/hudson/model/Fingerprint.java +++ b/core/src/main/java/hudson/model/Fingerprint.java @@ -724,7 +724,7 @@ public class Fingerprint implements ModelObject, Saveable { } void addWithoutSaving(String jobFullName, int n) { - synchronized(usages) { // XXX why not synchronized (this) like some, though not all, other accesses? + synchronized(usages) { // TODO why not synchronized (this) like some, though not all, other accesses? RangeSet r = usages.get(jobFullName); if(r==null) { r = new RangeSet(); diff --git a/core/src/main/java/hudson/model/JDK.java b/core/src/main/java/hudson/model/JDK.java index 73ca0c9db1..dbf9b2dcad 100644 --- a/core/src/main/java/hudson/model/JDK.java +++ b/core/src/main/java/hudson/model/JDK.java @@ -149,7 +149,7 @@ public final class JDK extends ToolInstallation implements NodeSpecific, En public static class DescriptorImpl extends ToolDescriptor { public String getDisplayName() { - return "JDK"; // XXX I18N + return "JDK"; // TODO I18N } public @Override JDK[] getInstallations() { diff --git a/core/src/main/java/hudson/model/Run.java b/core/src/main/java/hudson/model/Run.java index 474738068b..ef98acb584 100644 --- a/core/src/main/java/hudson/model/Run.java +++ b/core/src/main/java/hudson/model/Run.java @@ -1369,7 +1369,7 @@ public abstract class Run ,RunT extends Run,RunT extends Run getUnprotectedRootActions() { Set names = new TreeSet(); - names.add("jnlpJars"); // XXX cleaner to refactor doJnlpJars into a URA - // XXX consider caching (expiring cache when actions changes) + names.add("jnlpJars"); // TODO cleaner to refactor doJnlpJars into a URA + // TODO consider caching (expiring cache when actions changes) for (Action a : getActions()) { if (a instanceof UnprotectedRootAction) { names.add(a.getUrlName()); diff --git a/core/src/main/java/jenkins/model/lazy/BuildReferenceMapAdapter.java b/core/src/main/java/jenkins/model/lazy/BuildReferenceMapAdapter.java index acc5a10372..362138a2ac 100644 --- a/core/src/main/java/jenkins/model/lazy/BuildReferenceMapAdapter.java +++ b/core/src/main/java/jenkins/model/lazy/BuildReferenceMapAdapter.java @@ -100,7 +100,7 @@ class BuildReferenceMapAdapter implements SortedMap { } public boolean containsValue(Object value) { - return core.containsValue(value); // XXX should this be core.containsValue(wrap(value))? + return core.containsValue(value); // TODO should this be core.containsValue(wrap(value))? } public R get(Object key) { @@ -126,7 +126,7 @@ class BuildReferenceMapAdapter implements SortedMap { @Override public boolean equals(Object o) { - return core.equals(o); // XXX this is wrong + return core.equals(o); // TODO this is wrong } @Override diff --git a/core/src/main/resources/hudson/AboutJenkins/index.jelly b/core/src/main/resources/hudson/AboutJenkins/index.jelly index 4b4a5ba458..8b43cd979f 100644 --- a/core/src/main/resources/hudson/AboutJenkins/index.jelly +++ b/core/src/main/resources/hudson/AboutJenkins/index.jelly @@ -48,7 +48,7 @@ THE SOFTWARE.

        ${%plugin.dependencies}