diff --git a/spring-boot-tools/spring-boot-gradle-plugin/src/main/groovy/org/springframework/boot/gradle/SpringBootPluginExtension.groovy b/spring-boot-tools/spring-boot-gradle-plugin/src/main/groovy/org/springframework/boot/gradle/SpringBootPluginExtension.groovy index 19afbb24559..cd36bc8592c 100644 --- a/spring-boot-tools/spring-boot-gradle-plugin/src/main/groovy/org/springframework/boot/gradle/SpringBootPluginExtension.groovy +++ b/spring-boot-tools/spring-boot-gradle-plugin/src/main/groovy/org/springframework/boot/gradle/SpringBootPluginExtension.groovy @@ -16,13 +16,35 @@ package org.springframework.boot.gradle +import org.springframework.boot.loader.tools.Layout +import org.springframework.boot.loader.tools.Layouts + /** - * Gradle DSL Extension for 'Spring Boot'. + * Gradle DSL Extension for 'Spring Boot'. Most of the time Spring Boot can guess the + * settings in this extension, but occasionally you might need to explicitly set one + * or two of them. E.g. + * + *
+ * apply plugin: "spring-boot" + * springBoot { + * mainClass = 'org.demo.Application' + * layout = 'ZIP' + * } + ** * @author Phillip Webb + * @author Dave Syer */ public class SpringBootPluginExtension { + static enum LayoutType { + JAR(new Layouts.Jar()), WAR(new Layouts.War()), ZIP(new Layouts.Expanded()), DIR(new Layouts.Expanded()); + Layout layout; + private LayoutType(Layout layout) { + this.layout = layout; + } + } + /** * The main class that should be run. If not specified the value from the * MANIFEST will be used, or if no manifest entry is the archive will be @@ -31,7 +53,8 @@ public class SpringBootPluginExtension { String mainClass /** - * The name of the provided configuration. If not specified 'providedRuntime' will + * The name of the ivy configuration name to treat as 'provided' (when packaging + * those dependencies in a separate path). If not specified 'providedRuntime' will * be used. */ String providedConfiguration @@ -40,4 +63,23 @@ public class SpringBootPluginExtension { * If the original source archive should be backed-up before being repackaged. */ boolean backupSource = true; + + /** + * The layout of the archive if it can't be derived from the file extension. + * Valid values are JAR, WAR, ZIP, DIR (for exploded zip file). ZIP and DIR + * are actually synonymous, and should be used if there is no MANIFEST.MF + * available, or if you want the MANIFEST.MF 'Main-Class' to be + * PropertiesLauncher. Gradle will coerce literal String values to the + * correct type. + */ + LayoutType layout; + + /** + * Convenience method for use in a custom task. + * + * @return the Layout to use or null if not explicitly set + */ + Layout convertLayout() { + layout==null ? null : layout.layout + } } diff --git a/spring-boot-tools/spring-boot-gradle-plugin/src/main/groovy/org/springframework/boot/gradle/task/Repackage.java b/spring-boot-tools/spring-boot-gradle-plugin/src/main/groovy/org/springframework/boot/gradle/task/Repackage.java index 9b455ae0775..521a936e184 100644 --- a/spring-boot-tools/spring-boot-gradle-plugin/src/main/groovy/org/springframework/boot/gradle/task/Repackage.java +++ b/spring-boot-tools/spring-boot-gradle-plugin/src/main/groovy/org/springframework/boot/gradle/task/Repackage.java @@ -50,11 +50,13 @@ public class Repackage extends DefaultTask { if (file.exists()) { Repackager repackager = new Repackager(file); repackager.setMainClass(extension.getMainClass()); + if (extension.convertLayout() != null) { + repackager.setLayout(extension.convertLayout()); + } repackager.setBackupSource(extension.isBackupSource()); try { repackager.repackage(libraries); - } - catch (IOException ex) { + } catch (IOException ex) { throw new IllegalStateException(ex.getMessage(), ex); } } diff --git a/spring-boot-tools/spring-boot-gradle-plugin/src/main/resources/org/springframework/boot/git.properties b/spring-boot-tools/spring-boot-gradle-plugin/src/main/resources/org/springframework/boot/git.properties index 4c71ec6a6bc..ec98f87d954 100644 --- a/spring-boot-tools/spring-boot-gradle-plugin/src/main/resources/org/springframework/boot/git.properties +++ b/spring-boot-tools/spring-boot-gradle-plugin/src/main/resources/org/springframework/boot/git.properties @@ -1,13 +1,13 @@ #Generated by Git-Commit-Id-Plugin -#Tue Oct 15 11:07:38 EDT 2013 -git.commit.id.abbrev=d3fa609 +#Tue Oct 15 11:35:18 EDT 2013 +git.commit.id.abbrev=ea11daf git.commit.user.email=dsyer@gopivotal.com git.commit.message.full=Extend PropertiesLauncher to load nested archives\n\nPropertiesLauncher can now be used to run an executable jar, and by\ndefault it will pick up nested archives in lib/ (where the Boot\ntools puts them). User can provide loader.path (colon-separated)\nto change the nested path.\n\n[\#58837492] [bs-330] Add tooling for PropertiesLauncher\n -git.commit.id=d3fa60955b06fe78bbf0c914928d794661aca312 +git.commit.id=ea11dafcbd951b3b23257585bce1f479ca9faa73 git.commit.message.short=Extend PropertiesLauncher to load nested archives git.commit.user.name=Dave Syer git.build.user.name=Dave Syer git.build.user.email=dsyer@gopivotal.com git.branch=master -git.commit.time=2013-10-15T10\:51\:03-0400 -git.build.time=2013-10-15T11\:07\:38-0400 +git.commit.time=2013-10-15T11\:08\:45-0400 +git.build.time=2013-10-15T11\:35\:18-0400 diff --git a/spring-boot-tools/spring-boot-loader-tools/src/main/java/org/springframework/boot/loader/tools/Layouts.java b/spring-boot-tools/spring-boot-loader-tools/src/main/java/org/springframework/boot/loader/tools/Layouts.java index b3e2d3becf8..32ac121f60a 100644 --- a/spring-boot-tools/spring-boot-loader-tools/src/main/java/org/springframework/boot/loader/tools/Layouts.java +++ b/spring-boot-tools/spring-boot-loader-tools/src/main/java/org/springframework/boot/loader/tools/Layouts.java @@ -43,6 +43,9 @@ public class Layouts { if (file.getName().toLowerCase().endsWith(".war")) { return new War(); } + if (file.isDirectory() || file.getName().toLowerCase().endsWith(".zip")) { + return new Expanded(); + } throw new IllegalStateException("Unable to deduce layout for '" + file + "'"); } @@ -67,6 +70,18 @@ public class Layouts { } } + /** + * Executable expanded archive layout. + */ + public static class Expanded extends Jar { + + @Override + public String getLauncherClassName() { + return "org.springframework.boot.loader.PropertiesLauncher"; + } + + } + /** * Executable WAR layout. */ diff --git a/spring-boot-tools/spring-boot-loader-tools/src/main/resources/org/springframework/boot/git.properties b/spring-boot-tools/spring-boot-loader-tools/src/main/resources/org/springframework/boot/git.properties index c284d0a7ad7..7cea85057ff 100644 --- a/spring-boot-tools/spring-boot-loader-tools/src/main/resources/org/springframework/boot/git.properties +++ b/spring-boot-tools/spring-boot-loader-tools/src/main/resources/org/springframework/boot/git.properties @@ -1,13 +1,13 @@ #Generated by Git-Commit-Id-Plugin -#Tue Oct 15 11:07:33 EDT 2013 -git.commit.id.abbrev=d3fa609 +#Wed Oct 16 08:14:33 EDT 2013 +git.commit.id.abbrev=a7ba9ba git.commit.user.email=dsyer@gopivotal.com -git.commit.message.full=Extend PropertiesLauncher to load nested archives\n\nPropertiesLauncher can now be used to run an executable jar, and by\ndefault it will pick up nested archives in lib/ (where the Boot\ntools puts them). User can provide loader.path (colon-separated)\nto change the nested path.\n\n[\#58837492] [bs-330] Add tooling for PropertiesLauncher\n -git.commit.id=d3fa60955b06fe78bbf0c914928d794661aca312 -git.commit.message.short=Extend PropertiesLauncher to load nested archives +git.commit.message.full=Tooling for PropertiesLauncher\n +git.commit.id=a7ba9ba5cd47a924f9c7668a772957fc05ffa058 +git.commit.message.short=Tooling for PropertiesLauncher git.commit.user.name=Dave Syer git.build.user.name=Dave Syer git.build.user.email=dsyer@gopivotal.com -git.branch=master -git.commit.time=2013-10-15T10\:51\:03-0400 -git.build.time=2013-10-15T11\:07\:33-0400 +git.branch=feature/proptool +git.commit.time=2013-10-15T16\:54\:14-0400 +git.build.time=2013-10-16T08\:14\:33-0400 diff --git a/spring-boot-tools/spring-boot-loader/src/main/java/org/springframework/boot/loader/archive/Archive.java b/spring-boot-tools/spring-boot-loader/src/main/java/org/springframework/boot/loader/archive/Archive.java index 8bc7acbcc36..fd28fe63c53 100644 --- a/spring-boot-tools/spring-boot-loader/src/main/java/org/springframework/boot/loader/archive/Archive.java +++ b/spring-boot-tools/spring-boot-loader/src/main/java/org/springframework/boot/loader/archive/Archive.java @@ -47,9 +47,21 @@ public abstract class Archive { * @throws Exception */ public String getMainClass() throws Exception { - String mainClass = getManifest().getMainAttributes().getValue("Start-Class"); + Manifest manifest = getManifest(); + String mainClass = null; + if (manifest != null) { + mainClass = manifest.getMainAttributes().getValue("Start-Class"); + } if (mainClass == null) { - throw new IllegalStateException("No 'Start-Class' manifest entry specified"); + String url = "UNKNOWN"; + try { + url = getUrl().toString(); + } + catch (Exception e) { + // ignore + } + throw new IllegalStateException( + "No 'Start-Class' manifest entry specified in " + url); } return mainClass; } diff --git a/spring-boot-tools/spring-boot-loader/src/main/resources/org/springframework/boot/git.properties b/spring-boot-tools/spring-boot-loader/src/main/resources/org/springframework/boot/git.properties index 35fc5e979aa..10e364fba2c 100644 --- a/spring-boot-tools/spring-boot-loader/src/main/resources/org/springframework/boot/git.properties +++ b/spring-boot-tools/spring-boot-loader/src/main/resources/org/springframework/boot/git.properties @@ -1,13 +1,13 @@ #Generated by Git-Commit-Id-Plugin -#Tue Oct 15 11:07:32 EDT 2013 -git.commit.id.abbrev=d3fa609 +#Wed Oct 16 08:17:37 EDT 2013 +git.commit.id.abbrev=a7ba9ba git.commit.user.email=dsyer@gopivotal.com -git.commit.message.full=Extend PropertiesLauncher to load nested archives\n\nPropertiesLauncher can now be used to run an executable jar, and by\ndefault it will pick up nested archives in lib/ (where the Boot\ntools puts them). User can provide loader.path (colon-separated)\nto change the nested path.\n\n[\#58837492] [bs-330] Add tooling for PropertiesLauncher\n -git.commit.id=d3fa60955b06fe78bbf0c914928d794661aca312 -git.commit.message.short=Extend PropertiesLauncher to load nested archives +git.commit.message.full=Tooling for PropertiesLauncher\n +git.commit.id=a7ba9ba5cd47a924f9c7668a772957fc05ffa058 +git.commit.message.short=Tooling for PropertiesLauncher git.commit.user.name=Dave Syer git.build.user.name=Dave Syer git.build.user.email=dsyer@gopivotal.com -git.branch=master -git.commit.time=2013-10-15T10\:51\:03-0400 -git.build.time=2013-10-15T11\:07\:32-0400 +git.branch=feature/proptool +git.commit.time=2013-10-15T16\:54\:14-0400 +git.build.time=2013-10-16T08\:17\:37-0400 diff --git a/spring-boot-tools/spring-boot-maven-plugin/src/it/prop/pom.xml b/spring-boot-tools/spring-boot-maven-plugin/src/it/prop/pom.xml new file mode 100644 index 00000000000..56b0b7cd6c3 --- /dev/null +++ b/spring-boot-tools/spring-boot-maven-plugin/src/it/prop/pom.xml @@ -0,0 +1,53 @@ + +