Skip to content

Commit 7b5f46d

Browse files
committed
Add Spring-Boot-* manifest attributes to jars and wars built with Gradle
Closes gh-16068
1 parent 336af93 commit 7b5f46d

File tree

6 files changed

+47
-28
lines changed

6 files changed

+47
-28
lines changed

spring-boot-project/spring-boot-tools/spring-boot-gradle-plugin/src/main/java/org/springframework/boot/gradle/tasks/bundling/BootArchiveSupport.java

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2012-2018 the original author or authors.
2+
* Copyright 2012-2019 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -73,10 +73,20 @@ class BootArchiveSupport {
7373
configureExclusions();
7474
}
7575

76-
void configureManifest(Jar jar, String mainClassName) {
76+
void configureManifest(Jar jar, String mainClassName, String springBootClasses,
77+
String springBootLib) {
7778
Attributes attributes = jar.getManifest().getAttributes();
7879
attributes.putIfAbsent("Main-Class", this.loaderMainClass);
7980
attributes.putIfAbsent("Start-Class", mainClassName);
81+
attributes.computeIfAbsent("Spring-Boot-Version",
82+
(key) -> determineSpringBootVersion());
83+
attributes.putIfAbsent("Spring-Boot-Classes", springBootClasses);
84+
attributes.putIfAbsent("Spring-Boot-Lib", springBootLib);
85+
}
86+
87+
private String determineSpringBootVersion() {
88+
String implementationVersion = getClass().getPackage().getImplementationVersion();
89+
return (implementationVersion != null) ? implementationVersion : "unknown";
8090
}
8191

8292
CopyAction createCopyAction(Jar jar) {

spring-boot-project/spring-boot-tools/spring-boot-gradle-plugin/src/main/java/org/springframework/boot/gradle/tasks/bundling/BootJar.java

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2012-2018 the original author or authors.
2+
* Copyright 2012-2019 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -65,7 +65,8 @@ private Action<CopySpec> classpathFiles(Spec<File> filter) {
6565

6666
@Override
6767
public void copy() {
68-
this.support.configureManifest(this, getMainClassName());
68+
this.support.configureManifest(this, getMainClassName(), "BOOT-INF/classes/",
69+
"BOOT-INF/lib/");
6970
super.copy();
7071
}
7172

spring-boot-project/spring-boot-tools/spring-boot-gradle-plugin/src/main/java/org/springframework/boot/gradle/tasks/bundling/BootWar.java

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2012-2018 the original author or authors.
2+
* Copyright 2012-2019 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -57,7 +57,8 @@ public BootWar() {
5757

5858
@Override
5959
public void copy() {
60-
this.support.configureManifest(this, getMainClassName());
60+
this.support.configureManifest(this, getMainClassName(), "WEB-INF/classes/",
61+
"WEB-INF/lib/");
6162
super.copy();
6263
}
6364

spring-boot-project/spring-boot-tools/spring-boot-gradle-plugin/src/test/java/org/springframework/boot/gradle/tasks/bundling/AbstractBootArchiveTests.java

Lines changed: 24 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2012-2018 the original author or authors.
2+
* Copyright 2012-2019 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -97,6 +97,13 @@ public void basicArchiveCreation() throws IOException {
9797
.isEqualTo(this.launcherClass);
9898
assertThat(jarFile.getManifest().getMainAttributes().getValue("Start-Class"))
9999
.isEqualTo("com.example.Main");
100+
assertThat(jarFile.getManifest().getMainAttributes()
101+
.getValue("Spring-Boot-Classes")).isEqualTo(this.classesPath);
102+
assertThat(
103+
jarFile.getManifest().getMainAttributes().getValue("Spring-Boot-Lib"))
104+
.isEqualTo(this.libPath);
105+
assertThat(jarFile.getManifest().getMainAttributes()
106+
.getValue("Spring-Boot-Version")).isNotNull();
100107
}
101108
}
102109

@@ -106,8 +113,8 @@ public void classpathJarsArePackagedBeneathLibPath() throws IOException {
106113
this.task.classpath(this.temp.newFile("one.jar"), this.temp.newFile("two.jar"));
107114
this.task.execute();
108115
try (JarFile jarFile = new JarFile(this.task.getArchivePath())) {
109-
assertThat(jarFile.getEntry(this.libPath + "/one.jar")).isNotNull();
110-
assertThat(jarFile.getEntry(this.libPath + "/two.jar")).isNotNull();
116+
assertThat(jarFile.getEntry(this.libPath + "one.jar")).isNotNull();
117+
assertThat(jarFile.getEntry(this.libPath + "two.jar")).isNotNull();
111118
}
112119
}
113120

@@ -123,7 +130,7 @@ public void classpathFoldersArePackagedBeneathClassesPath() throws IOException {
123130
this.task.execute();
124131
try (JarFile jarFile = new JarFile(this.task.getArchivePath())) {
125132
assertThat(
126-
jarFile.getEntry(this.classesPath + "/com/example/Application.class"))
133+
jarFile.getEntry(this.classesPath + "com/example/Application.class"))
127134
.isNotNull();
128135
}
129136
}
@@ -136,8 +143,8 @@ public void classpathCanBeSetUsingAFileCollection() throws IOException {
136143
.setClasspath(this.task.getProject().files(this.temp.newFile("two.jar")));
137144
this.task.execute();
138145
try (JarFile jarFile = new JarFile(this.task.getArchivePath())) {
139-
assertThat(jarFile.getEntry(this.libPath + "/one.jar")).isNull();
140-
assertThat(jarFile.getEntry(this.libPath + "/two.jar")).isNotNull();
146+
assertThat(jarFile.getEntry(this.libPath + "one.jar")).isNull();
147+
assertThat(jarFile.getEntry(this.libPath + "two.jar")).isNotNull();
141148
}
142149
}
143150

@@ -148,8 +155,8 @@ public void classpathCanBeSetUsingAnObject() throws IOException {
148155
this.task.setClasspath(this.temp.newFile("two.jar"));
149156
this.task.execute();
150157
try (JarFile jarFile = new JarFile(this.task.getArchivePath())) {
151-
assertThat(jarFile.getEntry(this.libPath + "/one.jar")).isNull();
152-
assertThat(jarFile.getEntry(this.libPath + "/two.jar")).isNotNull();
158+
assertThat(jarFile.getEntry(this.libPath + "one.jar")).isNull();
159+
assertThat(jarFile.getEntry(this.libPath + "two.jar")).isNotNull();
153160
}
154161
}
155162

@@ -187,9 +194,9 @@ public void unpackCommentIsAddedToEntryIdentifiedByAPattern() throws IOException
187194
this.task.requiresUnpack("**/one.jar");
188195
this.task.execute();
189196
try (JarFile jarFile = new JarFile(this.task.getArchivePath())) {
190-
assertThat(jarFile.getEntry(this.libPath + "/one.jar").getComment())
197+
assertThat(jarFile.getEntry(this.libPath + "one.jar").getComment())
191198
.startsWith("UNPACK:");
192-
assertThat(jarFile.getEntry(this.libPath + "/two.jar").getComment()).isNull();
199+
assertThat(jarFile.getEntry(this.libPath + "two.jar").getComment()).isNull();
193200
}
194201
}
195202

@@ -200,9 +207,9 @@ public void unpackCommentIsAddedToEntryIdentifiedByASpec() throws IOException {
200207
this.task.requiresUnpack((element) -> element.getName().endsWith("two.jar"));
201208
this.task.execute();
202209
try (JarFile jarFile = new JarFile(this.task.getArchivePath())) {
203-
assertThat(jarFile.getEntry(this.libPath + "/two.jar").getComment())
210+
assertThat(jarFile.getEntry(this.libPath + "two.jar").getComment())
204211
.startsWith("UNPACK:");
205-
assertThat(jarFile.getEntry(this.libPath + "/one.jar").getComment()).isNull();
212+
assertThat(jarFile.getEntry(this.libPath + "one.jar").getComment()).isNull();
206213
}
207214
}
208215

@@ -322,7 +329,7 @@ public void devtoolsJarIsExcludedByDefault() throws IOException {
322329
this.task.execute();
323330
assertThat(this.task.getArchivePath()).exists();
324331
try (JarFile jarFile = new JarFile(this.task.getArchivePath())) {
325-
assertThat(jarFile.getEntry(this.libPath + "/spring-boot-devtools-0.1.2.jar"))
332+
assertThat(jarFile.getEntry(this.libPath + "spring-boot-devtools-0.1.2.jar"))
326333
.isNull();
327334
}
328335
}
@@ -335,7 +342,7 @@ public void devtoolsJarCanBeIncluded() throws IOException {
335342
this.task.execute();
336343
assertThat(this.task.getArchivePath()).exists();
337344
try (JarFile jarFile = new JarFile(this.task.getArchivePath())) {
338-
assertThat(jarFile.getEntry(this.libPath + "/spring-boot-devtools-0.1.2.jar"))
345+
assertThat(jarFile.getEntry(this.libPath + "spring-boot-devtools-0.1.2.jar"))
339346
.isNotNull();
340347
}
341348
}
@@ -377,9 +384,9 @@ public void loaderIsWrittenFirstThenApplicationClassesThenLibraries()
377384
this.task.execute();
378385
assertThat(getEntryNames(this.task.getArchivePath())).containsSubsequence(
379386
"org/springframework/boot/loader/",
380-
this.classesPath + "/com/example/Application.class",
381-
this.libPath + "/first-library.jar", this.libPath + "/second-library.jar",
382-
this.libPath + "/third-library.jar");
387+
this.classesPath + "com/example/Application.class",
388+
this.libPath + "first-library.jar", this.libPath + "second-library.jar",
389+
this.libPath + "third-library.jar");
383390
}
384391

385392
private T configure(T task) throws IOException {

spring-boot-project/spring-boot-tools/spring-boot-gradle-plugin/src/test/java/org/springframework/boot/gradle/tasks/bundling/BootJarTests.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2012-2018 the original author or authors.
2+
* Copyright 2012-2019 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -33,7 +33,7 @@ public class BootJarTests extends AbstractBootArchiveTests<BootJar> {
3333

3434
public BootJarTests() {
3535
super(BootJar.class, "org.springframework.boot.loader.JarLauncher",
36-
"BOOT-INF/lib", "BOOT-INF/classes");
36+
"BOOT-INF/lib/", "BOOT-INF/classes/");
3737
}
3838

3939
@Test

spring-boot-project/spring-boot-tools/spring-boot-gradle-plugin/src/test/java/org/springframework/boot/gradle/tasks/bundling/BootWarTests.java

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2012-2018 the original author or authors.
2+
* Copyright 2012-2019 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -32,8 +32,8 @@
3232
public class BootWarTests extends AbstractBootArchiveTests<BootWar> {
3333

3434
public BootWarTests() {
35-
super(BootWar.class, "org.springframework.boot.loader.WarLauncher", "WEB-INF/lib",
36-
"WEB-INF/classes");
35+
super(BootWar.class, "org.springframework.boot.loader.WarLauncher",
36+
"WEB-INF/lib/", "WEB-INF/classes/");
3737
}
3838

3939
@Test

0 commit comments

Comments
 (0)