Add Kotlin DSL examples to Gradle Plugin's documentation

See gh-14585
pull/11125/merge
jnizet 6 years ago committed by Andy Wilkinson
parent f8f6b474eb
commit 5ed6c0d1ab

@ -26,6 +26,7 @@
<maven.version>3.5.4</maven.version>
<maven-resolver.version>1.1.1</maven-resolver.version>
<spock.version>1.0-groovy-2.4</spock.version>
<dependency-management-plugin.version>1.0.6.RELEASE</dependency-management-plugin.version>
</properties>
<scm>
<url>http://github.com/spring-projects/spring-boot</url>
@ -108,7 +109,7 @@
<dependency>
<groupId>io.spring.gradle</groupId>
<artifactId>dependency-management-plugin</artifactId>
<version>1.0.6.RELEASE</version>
<version>${dependency-management-plugin.version}</version>
</dependency>
<dependency>
<groupId>jline</groupId>

@ -128,6 +128,13 @@
</plugin>
</plugins>
</build>
<pluginRepositories>
<pluginRepository>
<id>springio</id>
<name>Spring IO releases repository</name>
<url>https://repo.spring.io/release</url>
</pluginRepository>
</pluginRepositories>
<profiles>
<profile>
<id>windows</id>
@ -275,6 +282,7 @@
<github-tag>${github-tag}</github-tag>
<version-type>${version-type}</version-type>
<version>${project.version}</version>
<dependency-management-plugin-version>${dependency-management-plugin.version}</dependency-management-plugin-version>
</attributes>
</configuration>
<dependencies>
@ -283,6 +291,11 @@
<artifactId>asciidoctorj-pdf</artifactId>
<version>1.5.0-alpha.11</version>
</dependency>
<dependency>
<groupId>io.spring.asciidoctor</groupId>
<artifactId>spring-asciidoctor-extensions</artifactId>
<version>0.1.3.RELEASE</version>
</dependency>
</dependencies>
</plugin>
<plugin>

@ -6,22 +6,91 @@ To get started with the plugin it needs to be applied to your project.
ifeval::["{version-type}" == "RELEASE"]
The plugin is https://plugins.gradle.org/plugin/org.springframework.boot[published to
Gradle's plugin portal] and can be applied using the `plugins` block:
[source,groovy,indent=0,subs="verbatim,attributes"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/getting-started/apply-plugin-release.gradle[]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/getting-started/apply-plugin-release.gradle.kts[]
----
endif::[]
ifeval::["{version-type}" == "MILESTONE"]
The plugin is published to the Spring milestones repository.
For Gradle versions less than 4.10, you must apply the plugin imperatively:
[source,groovy,indent=0,subs="verbatim,attributes"]
----
include::../gradle/getting-started/apply-plugin-milestone.gradle[]
----
For Gradle 4.10 and above, it can be applied using the `plugins` block:
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/getting-started/apply-plugin-release.gradle[]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/getting-started/apply-plugin-release.gradle.kts[]
----
provided you add the following lines in the `settings.gradle` file (or `settings.gradle.kts` in Kotlin):
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/getting-started/milestone-settings.gradle[]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/getting-started/milestone-settings.gradle.kts[]
----
endif::[]
ifeval::["{version-type}" == "SNAPSHOT"]
The plugin is published to the Spring snapshots repository.
For Gradle versions less than 4.10, you must apply the plugin imperatively:
[source,groovy,indent=0,subs="verbatim,attributes"]
----
include::../gradle/getting-started/apply-plugin-snapshot.gradle[]
----
For Gradle 4.10 and above, it can be applied using the `plugins` block:
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/getting-started/apply-plugin-release.gradle[]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/getting-started/apply-plugin-release.gradle.kts[]
----
provided you add the following lines in the `settings.gradle` file (or `settings.gradle.kts` in Kotlin):
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/getting-started/snapshot-settings.gradle[]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/getting-started/snapshot-settings.gradle.kts[]
----
endif::[]
Applied in isolation the plugin makes few changes to a project. Instead, the plugin
@ -34,10 +103,18 @@ A typical Spring Boot project will apply the {groovy-plugin}[`groovy`],
plugin and the {dependency-management-plugin}[`io.spring.dependency-management`] plugin as
a minimum. For example:
[source,groovy,indent=0,subs="verbatim,attributes"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/getting-started/typical-plugins.gradle[tags=apply]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/getting-started/typical-plugins.gradle.kts[tags=apply]
----
To learn more about how the Spring Boot plugin behaves when other plugins are applied
please see the section on <<reacting-to-other-plugins, reacting to other plugins>>.

@ -37,7 +37,8 @@ Andy Wilkinson
The Spring Boot Gradle Plugin provides Spring Boot support in https://gradle.org[Gradle],
allowing you to package executable jar or war archives, run Spring Boot applications, and
use the dependency management provided by `spring-boot-dependencies`. Spring Boot's
Gradle plugin requires Gradle 4.4 or later.
Gradle plugin requires Gradle 4.4 or later. If you choose to use the newer Kotlin DSL,
it requires Gradle 4.10 or later.
In addition to this user guide, {api-documentation}[API documentation] is also available.
@ -47,4 +48,4 @@ include::packaging.adoc[]
include::publishing.adoc[]
include::running.adoc[]
include::integrating-with-actuator.adoc[]
include::reacting.adoc[]
include::reacting.adoc[]

@ -10,11 +10,19 @@ build in the presence of a `META-INF/build-info.properties` file. A
{build-info-javadoc}[`BuildInfo`] task is provided to generate this file. The easiest way
to use the task is via the plugin's DSL:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/integrating-with-actuator/build-info-basic.gradle[tags=build-info]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/integrating-with-actuator/build-info-basic.gradle.kts[tags=build-info]
----
This will configure a {build-info-javadoc}[`BuildInfo`] task named `bootBuildInfo` and, if
it exists, make the Java plugin's `classes` task depend upon it. The task's destination
directory will be `META-INF` in the output directory of the main source set's resources
@ -45,11 +53,19 @@ By default, the generated build information is derived from the project:
The properties can be customized using the DSL:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/integrating-with-actuator/build-info-custom-values.gradle[tags=custom-values]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/integrating-with-actuator/build-info-custom-values.gradle.kts[tags=custom-values]
----
The default value for `build.time` is the instant at which the project is being built. A
side-effect of this is that the task will never be up-to-date. As a result, builds will
take longer as more tasks, including the project's tests, will have to be executed.
@ -59,7 +75,15 @@ than the accuracy of the `build.time` property, set `time` to `null` or a fixed
Additional properties can also be added to the build information:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/integrating-with-actuator/build-info-additional.gradle[tags=additional]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/integrating-with-actuator/build-info-additional.gradle.kts[tags=additional]
----

@ -10,11 +10,17 @@ Maven users. For example, it allows you to omit version numbers when declaring
dependencies that are managed in the bom. To make use of this functionality, simply
declare dependencies in the usual way but omit the version number:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim",role="primary"]
.Groovy
----
include::../gradle/managing-dependencies/dependencies.gradle[tags=dependencies]
----
[source,kotlin,indent=0,subs="verbatim",role="secondary"]
.Kotlin
----
include::../gradle/managing-dependencies/dependencies.gradle.kts[tags=dependencies]
----
[[managing-dependencies-customizing]]
@ -28,11 +34,19 @@ for a complete list of these properties.
To customize a managed version you set its corresponding property. For example, to
customize the version of SLF4J which is controlled by the `slf4j.version` property:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim",role="primary"]
.Groovy
----
include::../gradle/managing-dependencies/custom-version.gradle[tags=custom-version]
----
[source,kotlin,indent=0,subs="verbatim",role="secondary"]
.Kotlin
----
include::../gradle/managing-dependencies/custom-version.gradle.kts[tags=custom-version]
----
WARNING: Each Spring Boot release is designed and tested against a specific set of
third-party dependencies. Overriding versions may cause compatibility issues and should
be done with care.
@ -50,21 +64,41 @@ artifact ID, or version.
First, configure the project to depend on the Spring Boot plugin but do not apply it:
ifeval::["{version-type}" == "RELEASE"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/managing-dependencies/depend-on-plugin-release.gradle[]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/managing-dependencies/depend-on-plugin-release.gradle.kts[]
----
endif::[]
ifeval::["{version-type}" == "MILESTONE"]
[source,groovy,indent=0,subs="verbatim,attributes"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/managing-dependencies/depend-on-plugin-milestone.gradle[]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/managing-dependencies/depend-on-plugin-release.gradle.kts[]
----
endif::[]
ifeval::["{version-type}" == "SNAPSHOT"]
[source,groovy,indent=0,subs="verbatim,attributes"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/managing-dependencies/depend-on-plugin-snapshot.gradle[]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/managing-dependencies/depend-on-plugin-release.gradle.kts[]
----
endif::[]
The Spring Boot plugin's dependency on the dependency management plugin means that you
@ -74,11 +108,31 @@ management plugin as Spring Boot uses.
Apply the dependency management plugin and then configure it to import Spring Boot's bom:
[source,groovy,indent=0,subs="verbatim,attributes"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/managing-dependencies/configure-bom.gradle[tags=configure-bom]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/managing-dependencies/configure-bom.gradle.kts[tags=configure-bom]
----
The Kotlin code above is a bit awkward. That's because we're using the imperative way of applying
the dependency management plugin.
We can make the code less awkward by applying the plugin from
the root parent project, or by using the `plugins` block as we're doing for the spring boot plugin.
The downside of this method, though, is that it forces us to specify the version of the
dependency management plugin, even though it's a dependency of the spring boot plugin:
[source,kotlin,indent=0,subs="verbatim,attributes"]
----
include::../gradle/managing-dependencies/configure-bom-with-plugins.gradle.kts[tags=configure-bom]
----
[[managing-dependencies-learning-more]]

@ -33,11 +33,19 @@ A war file can be packaged such that it can be executed using `java -jar` and de
to an external container. To do so, the embedded servlet container dependencies should
be added to the `providedRuntime` configuration, for example:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/war-container-dependency.gradle[tags=dependencies]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/war-container-dependency.gradle.kts[tags=dependencies]
----
This ensures that they are package in the war file's `WEB-INF/lib-provided` directory
from where they will not conflict with the external container's own classes.
@ -54,20 +62,36 @@ By default, when the `bootJar` or `bootWar` tasks are configured, the `jar` or `
tasks are disabled. A project can be configured to build both an executable archive
and a normal archive at the same time by enabling the `jar` or `war` task:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/boot-jar-and-jar.gradle[tags=enable-jar]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/boot-jar-and-jar.gradle.kts[tags=enable-jar]
----
To avoid the executable archive and the normal archive from being written to the same
location, one or the other should be configured to use a different location. One way to
do so is by configuring a classifier:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/boot-jar-and-jar.gradle[tags=classifier]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/boot-jar-and-jar.gradle.kts[tags=classifier]
----
[[packaging-executable-configuring]]
=== Configuring executable archive packaging
@ -88,34 +112,63 @@ the task's classpath.
The main class can also be configured explicitly using the task's `mainClassName`
property:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/boot-jar-main-class.gradle[tags=main-class]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/boot-jar-main-class.gradle.kts[tags=main-class]
----
Alternatively, the main class name can be configured project-wide using the
`mainClassName` property of the Spring Boot DSL:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/spring-boot-dsl-main-class.gradle[tags=main-class]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/spring-boot-dsl-main-class.gradle.kts[tags=main-class]
----
If the {application-plugin}[`application` plugin] has been applied its `mainClassName`
project property can be used for the same purpose:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/application-plugin-main-class.gradle[tags=main-class]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/application-plugin-main-class.gradle.kts[tags=main-class]
----
Lastly, the `Start-Class` attribute can be configured on the task's manifest:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/boot-jar-manifest-main-class.gradle[tags=main-class]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/boot-jar-manifest-main-class.gradle.kts[tags=main-class]
----
[[packaging-executable-configuring-excluding-devtools]]
@ -126,11 +179,17 @@ By default, Spring Boot's Devtools module,
or war. If you want to include Devtools in your archive set the `excludeDevtools`
property to `false`:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/boot-war-include-devtools.gradle[tags=include-devtools]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/boot-war-include-devtools.gradle.kts[tags=include-devtools]
----
[[packaging-executable-configuring-unpacking]]
@ -145,11 +204,19 @@ specific nested jars to a temporary folder when the executable archive is run. L
can be identified as requiring unpacking using Ant-style patterns that match against
the absolute path of the source jar file:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/boot-jar-requires-unpack.gradle[tags=requires-unpack]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/boot-jar-requires-unpack.gradle.kts[tags=requires-unpack]
----
For more control a closure can also be used. The closure is passed a `FileTreeElement`
and should return a `boolean` indicating whether or not unpacking is required.
@ -165,28 +232,50 @@ other executable or to be installed as a service.
To use this feature, the inclusion of the launch script must be enabled:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/boot-jar-include-launch-script.gradle[tags=include-launch-script]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/boot-jar-include-launch-script.gradle.kts[tags=include-launch-script]
----
This will add Spring Boot's default launch script to the archive. The default launch
script includes several properties with sensible default values. The values can be
customized using the `properties` property:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/boot-jar-launch-script-properties.gradle[tags=launch-script-properties]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/boot-jar-launch-script-properties.gradle.kts[tags=launch-script-properties]
----
If the default launch script does not meet your needs, the `script` property can be used
to provide a custom launch script:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/boot-jar-custom-launch-script.gradle[tags=custom-launch-script]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/boot-jar-custom-launch-script.gradle.kts[tags=custom-launch-script]
----
[[packaging-executable-configuring-properties-launcher]]
@ -195,7 +284,15 @@ include::../gradle/packaging/boot-jar-custom-launch-script.gradle[tags=custom-la
To use the `PropertiesLauncher` to launch an executable jar or war, configure the task's
manifest to set the `Main-Class` attribute:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/packaging/boot-war-properties-launcher.gradle[tags=properties-launcher]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/packaging/boot-war-properties-launcher.gradle.kts[tags=properties-launcher]
----

@ -12,11 +12,19 @@ default, the `bootArchives` configuration contains the archive produced by the `
or `bootWar` task. The `uploadBootArchives` task can be configured to publish the archive
to a Maven repository:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/publishing/maven.gradle[tags=upload]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/publishing/maven.gradle.kts[tags=upload]
----
[[publishing-your-application-maven-publish]]
=== Publishing with the `maven-publish` plugin
@ -25,11 +33,17 @@ method on `MavenPublication`. Pass the task that produces that artifact that you
to publish to the `artifact` method. For example, to publish the artifact produced by the
default `bootJar` task:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/publishing/maven-publish.gradle[tags=publishing]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/publishing/maven-publish.gradle.kts[tags=publishing]
----
[[publishing-your-application-distribution]]

@ -19,27 +19,49 @@ By default, the main class will be configured automatically by looking for a cla
The main class can also be configured explicitly using the task's `main` property:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/running/boot-run-main.gradle[tags=main]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/running/boot-run-main.gradle.kts[tags=main]
----
Alternatively, the main class name can be configured project-wide using the
`mainClassName` property of the Spring Boot DSL:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/running/spring-boot-dsl-main-class-name.gradle[tags=main-class]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/running/spring-boot-dsl-main-class-name.gradle.kts[tags=main-class]
----
If the {application-plugin}[`application` plugin] has been applied, its `mainClassName`
project property can be used for the same purpose:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/running/application-plugin-main-class-name.gradle[tags=main-class]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/running/application-plugin-main-class-name.gradle.kts[tags=main-class]
----
[[running-your-application-passing-arguments]]
@ -64,10 +86,18 @@ If devtools has been added to your project it will automatically monitor your
application for changes. Alternatively, you can configure `bootRun` such that your
application's static resources are loaded from their source location:
[source,groovy,indent=0,subs="verbatim"]
[source,groovy,indent=0,subs="verbatim,attributes",role="primary"]
.Groovy
----
include::../gradle/running/boot-run-source-resources.gradle[tags=source-resources]
----
[source,kotlin,indent=0,subs="verbatim,attributes",role="secondary"]
.Kotlin
----
include::../gradle/running/boot-run-source-resources.gradle.kts[tags=source-resources]
----
This makes them reloadable in the live application which can be helpful at development
time.

@ -0,0 +1,14 @@
pluginManagement {
repositories {
maven {
url 'https://repo.spring.io/libs-milestone'
}
}
resolutionStrategy {
eachPlugin {
if (requested.id.id == 'org.springframework.boot') {
useModule "org.springframework.boot:spring-boot-gradle-plugin:${requested.version}"
}
}
}
}

@ -0,0 +1,14 @@
pluginManagement {
repositories {
maven {
url = uri("https://repo.spring.io/libs-milestone")
}
}
resolutionStrategy {
eachPlugin {
if (requested.id.id == "org.springframework.boot") {
useModule("org.springframework.boot:spring-boot-gradle-plugin:${requested.version}")
}
}
}
}

@ -0,0 +1,14 @@
pluginManagement {
repositories {
maven {
url 'https://repo.spring.io/libs-snapshot'
}
}
resolutionStrategy {
eachPlugin {
if (requested.id.id == 'org.springframework.boot') {
useModule "org.springframework.boot:spring-boot-gradle-plugin:${requested.version}"
}
}
}
}

@ -0,0 +1,14 @@
pluginManagement {
repositories {
maven {
url = uri("https://repo.spring.io/libs-snapshot")
}
}
resolutionStrategy {
eachPlugin {
if (requested.id.id == "org.springframework.boot") {
useModule("org.springframework.boot:spring-boot-gradle-plugin:${requested.version}")
}
}
}
}

@ -0,0 +1,15 @@
// tag::apply[]
plugins {
java
id("org.springframework.boot") version "{version}"
}
apply(plugin = "io.spring.dependency-management")
// end::apply[]
task("verify") {
doLast {
project.plugins.getPlugin(JavaPlugin::class)
project.plugins.getPlugin(io.spring.gradle.dependencymanagement.DependencyManagementPlugin::class)
}
}

@ -0,0 +1,18 @@
plugins {
java
id("org.springframework.boot") version "{version}"
}
// tag::additional[]
springBoot {
buildInfo {
properties {
additional = mapOf(
"a" to "alpha",
"b" to "bravo"
)
}
}
}
// end::additional[]

@ -0,0 +1,10 @@
plugins {
java
id("org.springframework.boot") version "{version}"
}
// tag::build-info[]
springBoot {
buildInfo()
}
// end::build-info[]

@ -0,0 +1,17 @@
plugins {
java
id("org.springframework.boot") version "{version}"
}
// tag::custom-values[]
springBoot {
buildInfo {
properties {
artifact = "example-app"
version = "1.2.3"
group = "com.example"
name = "Example application"
}
}
}
// end::custom-values[]

@ -0,0 +1,27 @@
// tag::configure-bom[]
plugins {
java
id("org.springframework.boot") version "{version}" apply false
id("io.spring.dependency-management") version "{dependency-management-plugin-version}"
}
dependencyManagement {
imports {
mavenBom(org.springframework.boot.gradle.plugin.SpringBootPlugin.BOM_COORDINATES)
}
}
// end::configure-bom[]
dependencyManagement {
resolutionStrategy {
eachDependency {
if (requested.group == "org.springframework.boot") {
useVersion("{version}")
}
}
}
}
repositories {
mavenLocal()
}

@ -3,13 +3,21 @@ plugins {
id 'org.springframework.boot' version '{version}'
}
// tag::configure-bom[]
apply plugin: 'io.spring.dependency-management'
dependencyManagement {
imports {
mavenBom org.springframework.boot.gradle.plugin.SpringBootPlugin.BOM_COORDINATES
}
}
// end::configure-bom[]
dependencyManagement {
resolutionStrategy {
eachDependency {
if (it.requested.group == 'org.springframework.boot') {
it.useVersion project.bootVersion
it.useVersion '{version}'
}
}
}
@ -18,13 +26,3 @@ dependencyManagement {
repositories {
mavenLocal()
}
// tag::configure-bom[]
apply plugin: 'io.spring.dependency-management'
dependencyManagement {
imports {
mavenBom org.springframework.boot.gradle.plugin.SpringBootPlugin.BOM_COORDINATES
}
}
// end::configure-bom[]

@ -0,0 +1,30 @@
import io.spring.gradle.dependencymanagement.dsl.DependencyManagementExtension
plugins {
java
id("org.springframework.boot") version "{version}"
}
// tag::configure-bom[]
apply(plugin = "io.spring.dependency-management")
the<DependencyManagementExtension>().apply {
imports {
mavenBom(org.springframework.boot.gradle.plugin.SpringBootPlugin.BOM_COORDINATES)
}
}
// end::configure-bom[]
the<DependencyManagementExtension>().apply {
resolutionStrategy {
eachDependency {
if (requested.group == "org.springframework.boot") {
useVersion("{version}")
}
}
}
}
repositories {
mavenLocal()
}

@ -8,7 +8,7 @@ dependencyManagement {
resolutionStrategy {
eachDependency {
if (it.requested.group == 'org.springframework.boot') {
it.useVersion project.bootVersion
it.useVersion '{version}'
}
}
}

@ -0,0 +1,31 @@
import io.spring.gradle.dependencymanagement.dsl.DependencyManagementExtension
plugins {
id("org.springframework.boot") version "{version}"
}
apply(plugin = "io.spring.dependency-management")
the<DependencyManagementExtension>().apply {
resolutionStrategy {
eachDependency {
if (requested.group == "org.springframework.boot") {
useVersion("{version}")
}
}
}
}
// tag::custom-version[]
extra["slf4j.version"] = "1.7.20"
// end::custom-version[]
repositories {
mavenLocal()
}
task("slf4jVersion") {
doLast {
println(project.the<DependencyManagementExtension>().managedVersions["org.slf4j:slf4j-api"])
}
}

@ -0,0 +1,13 @@
plugins {
java
id("org.springframework.boot") version "{version}"
}
apply(plugin = "io.spring.dependency-management")
// tag::dependencies[]
dependencies {
implementation("org.springframework.boot:spring-boot-starter-web")
implementation("org.springframework.boot:spring-boot-starter-data-jpa")
}
// end::dependencies[]

@ -0,0 +1,11 @@
plugins {
java
application
id("org.springframework.boot") version "{version}"
}
// tag::main-class[]
application {
mainClassName = "com.example.ExampleApplication"
}
// end::main-class[]

@ -0,0 +1,22 @@
import org.springframework.boot.gradle.tasks.bundling.BootJar
plugins {
java
id("org.springframework.boot") version "{version}"
}
// tag::enable-jar[]
tasks.getByName<Jar>("jar") {
enabled = true
}
// end::enable-jar[]
// tag::classifier[]
tasks.getByName<BootJar>("bootJar") {
classifier = "boot"
}
// end::classifier[]
tasks.getByName<BootJar>("bootJar") {
mainClassName = "com.example.Application"
}

@ -0,0 +1,18 @@
import org.springframework.boot.gradle.tasks.bundling.BootJar
plugins {
java
id("org.springframework.boot") version "{version}"
}
tasks.getByName<BootJar>("bootJar") {
mainClassName = "com.example.ExampleApplication"
}
// tag::custom-launch-script[]
tasks.getByName<BootJar>("bootJar") {
launchScript {
script = file("src/custom.script")
}
}
// end::custom-launch-script[]

@ -0,0 +1,16 @@
import org.springframework.boot.gradle.tasks.bundling.BootJar
plugins {
java
id("org.springframework.boot") version "{version}"
}
tasks.getByName<BootJar>("bootJar") {
mainClassName = "com.example.ExampleApplication"
}
// tag::include-launch-script[]
tasks.getByName<BootJar>("bootJar") {
launchScript()
}
// end::include-launch-script[]

@ -0,0 +1,18 @@
import org.springframework.boot.gradle.tasks.bundling.BootJar
plugins {
java
id("org.springframework.boot") version "{version}"
}
tasks.getByName<BootJar>("bootJar") {
mainClassName = "com.example.ExampleApplication"
}
// tag::launch-script-properties[]
tasks.getByName<BootJar>("bootJar") {
launchScript {
properties(mapOf("logFilename" to "example-app.log"))
}
}
// end::launch-script-properties[]

@ -0,0 +1,12 @@
import org.springframework.boot.gradle.tasks.bundling.BootJar
plugins {
java
id("org.springframework.boot") version "{version}"
}
// tag::main-class[]
tasks.getByName<BootJar>("bootJar") {
mainClassName = "com.example.ExampleApplication"
}
// end::main-class[]

@ -0,0 +1,14 @@
import org.springframework.boot.gradle.tasks.bundling.BootJar
plugins {
java
id("org.springframework.boot") version "{version}"
}
// tag::main-class[]
tasks.getByName<BootJar>("bootJar") {
manifest {
attributes("Start-Class" to "com.example.ExampleApplication")
}
}
// end::main-class[]

@ -0,0 +1,24 @@
import org.springframework.boot.gradle.tasks.bundling.BootJar
plugins {
java
id("org.springframework.boot") version "{version}"
}
repositories {
mavenCentral()
}
dependencies {
runtimeOnly("org.jruby:jruby-complete:1.7.25")
}
tasks.getByName<BootJar>("bootJar") {
mainClassName = "com.example.ExampleApplication"
}
// tag::requires-unpack[]
tasks.getByName<BootJar>("bootJar") {
requiresUnpack("**/jruby-complete-*.jar")
}
// end::requires-unpack[]

@ -0,0 +1,17 @@
import org.springframework.boot.gradle.tasks.bundling.BootWar
plugins {
war
id("org.springframework.boot") version "{version}"
}
tasks.getByName<BootWar>("bootWar") {
mainClassName = "com.example.ExampleApplication"
classpath(file("spring-boot-devtools-1.2.3.RELEASE.jar"))
}
// tag::include-devtools[]
tasks.getByName<BootWar>("bootWar") {
isExcludeDevtools = false
}
// end::include-devtools[]

@ -0,0 +1,18 @@
import org.springframework.boot.gradle.tasks.bundling.BootWar
plugins {
war
id("org.springframework.boot") version "{version}"
}
tasks.getByName<BootWar>("bootWar") {
mainClassName = "com.example.ExampleApplication"
}
// tag::properties-launcher[]
tasks.getByName<BootWar>("bootWar") {
manifest {
attributes("Main-Class" to "org.springframework.boot.loader.PropertiesLauncher")
}
}
// end::properties-launcher[]

@ -0,0 +1,10 @@
plugins {
war
id("org.springframework.boot") version "{version}"
}
// tag::main-class[]
springBoot {
mainClassName = "com.example.ExampleApplication"
}
// end::main-class[]

@ -0,0 +1,13 @@
plugins {
war
id("org.springframework.boot") version "{version}"
}
apply(plugin = "io.spring.dependency-management")
// tag::dependencies[]
dependencies {
implementation("org.springframework.boot:spring-boot-starter-web")
providedRuntime("org.springframework.boot:spring-boot-starter-tomcat")
}
// end::dependencies[]

@ -0,0 +1,27 @@
plugins {
java
`maven-publish`
id("org.springframework.boot") version "{version}"
}
// tag::publishing[]
publishing {
publications {
create<MavenPublication>("bootJava") {
artifact(tasks.getByName("bootJar"))
}
}
repositories {
maven {
url = uri("https://repo.example.com")
}
}
}
// end::publishing[]
task("publishingConfiguration") {
doLast {
println(publishing.publications["bootJava"])
println(publishing.repositories.getByName<MavenArtifactRepository>("maven").url)
}
}

@ -0,0 +1,26 @@
plugins {
java
maven
id("org.springframework.boot") version "{version}"
}
// tag::upload[]
tasks.getByName<Upload>("uploadBootArchives") {
repositories.withGroovyBuilder {
"mavenDeployer" {
"repository"("url" to "https://repo.example.com")
}
}
}
// end::upload[]
val url = tasks.getByName<Upload>("uploadBootArchives")
.repositories
.withGroovyBuilder { getProperty("mavenDeployer") }
.withGroovyBuilder { getProperty("repository") }
.withGroovyBuilder { getProperty("url") }
task("deployerRepository") {
doLast {
println(url)
}
}

@ -0,0 +1,19 @@
import org.springframework.boot.gradle.tasks.run.BootRun
plugins {
java
application
id("org.springframework.boot") version "{version}"
}
// tag::main-class[]
application {
mainClassName = "com.example.ExampleApplication"
}
// end::main-class[]
task("configuredMainClass") {
doLast {
println(tasks.getByName<BootRun>("bootRun").main)
}
}

@ -0,0 +1,18 @@
import org.springframework.boot.gradle.tasks.run.BootRun
plugins {
java
id("org.springframework.boot") version "{version}"
}
// tag::main[]
tasks.getByName<BootRun>("bootRun") {
main = "com.example.ExampleApplication"
}
// end::main[]
task("configuredMainClass") {
doLast {
println(tasks.getByName<BootRun>("bootRun").main)
}
}

@ -0,0 +1,18 @@
import org.springframework.boot.gradle.tasks.run.BootRun
plugins {
java
id("org.springframework.boot") version "{version}"
}
// tag::source-resources[]
tasks.getByName<BootRun>("bootRun") {
sourceResources(sourceSets["main"])
}
// end::source-resources[]
task("configuredClasspath") {
doLast {
println(tasks.getByName<BootRun>("bootRun").classpath.files)
}
}

@ -0,0 +1,19 @@
import org.springframework.boot.gradle.tasks.run.BootRun
plugins {
java
application
id("org.springframework.boot") version "{version}"
}
// tag::main-class[]
springBoot {
mainClassName = "com.example.ExampleApplication"
}
// end::main-class[]
task("configuredMainClass") {
doLast {
println(tasks.getByName<BootRun>("bootRun").main)
}
}

@ -0,0 +1,48 @@
/*
* Copyright 2012-2018 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.boot.gradle.docs;
/**
* The DSLs supported by Gradle and demonstrated in the documentation samples
*/
public enum DSL {
GROOVY("Groovy", ".gradle"), KOTLIN("Kotlin", ".gradle.kts");
private final String name;
private final String extension;
DSL(String name, String extension) {
this.name = name;
this.extension = extension;
}
/**
* Gets the user-friendly name of the DSL
*/
public String getName() {
return this.name;
}
/**
* Gets the file extension of build scripts (starting with a dot)
*/
public String getExtension() {
return this.extension;
}
}

@ -18,6 +18,7 @@ package org.springframework.boot.gradle.docs;
import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.gradle.testkit.GradleBuild;
@ -25,19 +26,23 @@ import org.springframework.boot.gradle.testkit.GradleBuild;
* Tests for the getting started documentation.
*
* @author Andy Wilkinson
* @author Jean-Baptiste Nizet
*/
@RunWith(GradleMultiDslSuite.class)
public class GettingStartedDocumentationTests {
@Rule
public GradleBuild gradleBuild = new GradleBuild();
public GradleBuild gradleBuild;
public DSL dsl;
// NOTE: We can't run any `apply-plugin` tests because during a release the
// jar won't be there
@Test
public void typicalPluginsAppliesExceptedPlugins() {
this.gradleBuild.script("src/main/gradle/getting-started/typical-plugins.gradle")
.build("verify");
this.gradleBuild.script("src/main/gradle/getting-started/typical-plugins"
+ this.dsl.getExtension()).build("verify");
}
}

@ -0,0 +1,90 @@
/*
* Copyright 2012-2018 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.boot.gradle.docs;
import java.util.ArrayList;
import java.util.List;
import org.gradle.api.Rule;
import org.junit.runner.Runner;
import org.junit.runners.BlockJUnit4ClassRunner;
import org.junit.runners.Suite;
import org.junit.runners.model.FrameworkMethod;
import org.junit.runners.model.InitializationError;
import org.springframework.boot.gradle.testkit.GradleBuild;
/**
* Custom {@link Suite} that runs tests against the Groovy and the Kotlin DSLs. Test
* classes using the suite must have a public {@link DSL} field named {@code dsl} and a
* public {@link GradleBuild} field named {@code gradleBuild} and annotated with
* {@link Rule}
*
* @author Jean-Baptiste Nizet
*/
public final class GradleMultiDslSuite extends Suite {
public GradleMultiDslSuite(Class<?> clazz) throws InitializationError {
super(clazz, createRunners(clazz));
}
private static List<Runner> createRunners(Class<?> clazz) throws InitializationError {
List<Runner> runners = new ArrayList<>();
runners.add(new GradleDslClassRunner(clazz, new GradleBuild(), DSL.GROOVY));
runners.add(new GradleDslClassRunner(clazz,
new GradleBuild().withMinimalGradleVersionForKotlinDSL(), DSL.KOTLIN));
return runners;
}
private static final class GradleDslClassRunner extends BlockJUnit4ClassRunner {
private final GradleBuild gradleBuild;
private final DSL dsl;
private GradleDslClassRunner(Class<?> klass, GradleBuild gradleBuild, DSL dsl)
throws InitializationError {
super(klass);
this.gradleBuild = gradleBuild;
this.dsl = dsl;
}
@Override
protected Object createTest() throws Exception {
Object test = super.createTest();
configureTest(test);
return test;
}
private void configureTest(Object test) throws Exception {
test.getClass().getField("gradleBuild").set(test, this.gradleBuild);
test.getClass().getField("dsl").set(test, this.dsl);
}
@Override
protected String getName() {
return this.dsl.getName() + " DSL";
}
@Override
protected String testName(FrameworkMethod method) {
return method.getName() + " [" + getName() + "]";
}
}
}

@ -23,6 +23,7 @@ import java.util.Properties;
import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.gradle.testkit.GradleBuild;
@ -32,16 +33,21 @@ import static org.assertj.core.api.Assertions.assertThat;
* Tests for the generating build info documentation.
*
* @author Andy Wilkinson
* @author Jean-Baptiste Nizet
*/
@RunWith(GradleMultiDslSuite.class)
public class IntegratingWithActuatorDocumentationTests {
@Rule
public GradleBuild gradleBuild = new GradleBuild();
public GradleBuild gradleBuild;
public DSL dsl;
@Test
public void basicBuildInfo() throws IOException {
this.gradleBuild.script(
"src/main/gradle/integrating-with-actuator/build-info-basic.gradle")
this.gradleBuild
.script("src/main/gradle/integrating-with-actuator/build-info-basic"
+ this.dsl.getExtension())
.build("bootBuildInfo");
assertThat(new File(this.gradleBuild.getProjectDir(),
"build/resources/main/META-INF/build-info.properties")).isFile();
@ -50,7 +56,8 @@ public class IntegratingWithActuatorDocumentationTests {
@Test
public void buildInfoCustomValues() throws IOException {
this.gradleBuild.script(
"src/main/gradle/integrating-with-actuator/build-info-custom-values.gradle")
"src/main/gradle/integrating-with-actuator/build-info-custom-values"
+ this.dsl.getExtension())
.build("bootBuildInfo");
File file = new File(this.gradleBuild.getProjectDir(),
"build/resources/main/META-INF/build-info.properties");
@ -64,8 +71,9 @@ public class IntegratingWithActuatorDocumentationTests {
@Test
public void buildInfoAdditional() throws IOException {
this.gradleBuild.script(
"src/main/gradle/integrating-with-actuator/build-info-additional.gradle")
this.gradleBuild
.script("src/main/gradle/integrating-with-actuator/build-info-additional"
+ this.dsl.getExtension())
.build("bootBuildInfo");
File file = new File(this.gradleBuild.getProjectDir(),
"build/resources/main/META-INF/build-info.properties");

@ -18,6 +18,7 @@ package org.springframework.boot.gradle.docs;
import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.gradle.testkit.GradleBuild;
@ -27,32 +28,49 @@ import static org.assertj.core.api.Assertions.assertThat;
* Tests for the managing dependencies documentation.
*
* @author Andy Wilkinson
* @author Jean-Baptiste Nizet
*/
@RunWith(GradleMultiDslSuite.class)
public class ManagingDependenciesDocumentationTests {
@Rule
public GradleBuild gradleBuild = new GradleBuild();
public GradleBuild gradleBuild;
public DSL dsl;
@Test
public void dependenciesExampleEvaluatesSuccessfully() {
this.gradleBuild
.script("src/main/gradle/managing-dependencies/dependencies.gradle")
.build();
this.gradleBuild.script("src/main/gradle/managing-dependencies/dependencies"
+ this.dsl.getExtension()).build();
}
@Test
public void customManagedVersions() {
assertThat(this.gradleBuild
.script("src/main/gradle/managing-dependencies/custom-version.gradle")
.build("slf4jVersion").getOutput()).contains("1.7.20");
assertThat(
this.gradleBuild
.script("src/main/gradle/managing-dependencies/custom-version"
+ this.dsl.getExtension())
.build("slf4jVersion").getOutput()).contains("1.7.20");
}
@Test
public void dependencyManagementInIsolation() {
assertThat(this.gradleBuild
.script("src/main/gradle/managing-dependencies/configure-bom.gradle")
.script("src/main/gradle/managing-dependencies/configure-bom"
+ this.dsl.getExtension())
.build("dependencyManagement").getOutput())
.contains("org.springframework.boot:spring-boot-starter ");
}
@Test
public void dependencyManagementInIsolationWithPluginsBlock() {
if (this.dsl == DSL.KOTLIN) {
assertThat(this.gradleBuild.script(
"src/main/gradle/managing-dependencies/configure-bom-with-plugins"
+ this.dsl.getExtension())
.build("dependencyManagement").getOutput())
.contains("org.springframework.boot:spring-boot-starter ");
}
}
}

@ -25,6 +25,7 @@ import java.util.jar.JarFile;
import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.gradle.testkit.GradleBuild;
import org.springframework.util.FileCopyUtils;
@ -35,22 +36,26 @@ import static org.assertj.core.api.Assertions.assertThat;
* Tests for the packaging documentation.
*
* @author Andy Wilkinson
* @author Jean-Baptiste Nizet
*/
@RunWith(GradleMultiDslSuite.class)
public class PackagingDocumentationTests {
@Rule
public GradleBuild gradleBuild = new GradleBuild();
public GradleBuild gradleBuild;
public DSL dsl;
@Test
public void warContainerDependencyEvaluatesSuccessfully() {
this.gradleBuild
.script("src/main/gradle/packaging/war-container-dependency.gradle")
.build();
this.gradleBuild.script("src/main/gradle/packaging/war-container-dependency"
+ this.dsl.getExtension()).build();
}
@Test
public void bootJarMainClass() throws IOException {
this.gradleBuild.script("src/main/gradle/packaging/boot-jar-main-class.gradle")
this.gradleBuild.script(
"src/main/gradle/packaging/boot-jar-main-class" + this.dsl.getExtension())
.build("bootJar");
File file = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".jar");
@ -63,9 +68,8 @@ public class PackagingDocumentationTests {
@Test
public void bootJarManifestMainClass() throws IOException {
this.gradleBuild
.script("src/main/gradle/packaging/boot-jar-manifest-main-class.gradle")
.build("bootJar");
this.gradleBuild.script("src/main/gradle/packaging/boot-jar-manifest-main-class"
+ this.dsl.getExtension()).build("bootJar");
File file = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".jar");
assertThat(file).isFile();
@ -77,9 +81,8 @@ public class PackagingDocumentationTests {
@Test
public void applicationPluginMainClass() throws IOException {
this.gradleBuild
.script("src/main/gradle/packaging/application-plugin-main-class.gradle")
.build("bootJar");
this.gradleBuild.script("src/main/gradle/packaging/application-plugin-main-class"
+ this.dsl.getExtension()).build("bootJar");
File file = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".jar");
assertThat(file).isFile();
@ -91,9 +94,8 @@ public class PackagingDocumentationTests {
@Test
public void springBootDslMainClass() throws IOException {
this.gradleBuild
.script("src/main/gradle/packaging/spring-boot-dsl-main-class.gradle")
.build("bootJar");
this.gradleBuild.script("src/main/gradle/packaging/spring-boot-dsl-main-class"
+ this.dsl.getExtension()).build("bootJar");
File file = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".jar");
assertThat(file).isFile();
@ -107,9 +109,8 @@ public class PackagingDocumentationTests {
public void bootWarIncludeDevtools() throws IOException {
new File(this.gradleBuild.getProjectDir(),
"spring-boot-devtools-1.2.3.RELEASE.jar").createNewFile();
this.gradleBuild
.script("src/main/gradle/packaging/boot-war-include-devtools.gradle")
.build("bootWar");
this.gradleBuild.script("src/main/gradle/packaging/boot-war-include-devtools"
+ this.dsl.getExtension()).build("bootWar");
File file = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".war");
assertThat(file).isFile();
@ -121,9 +122,8 @@ public class PackagingDocumentationTests {
@Test
public void bootJarRequiresUnpack() throws IOException {
this.gradleBuild
.script("src/main/gradle/packaging/boot-jar-requires-unpack.gradle")
.build("bootJar");
this.gradleBuild.script("src/main/gradle/packaging/boot-jar-requires-unpack"
+ this.dsl.getExtension()).build("bootJar");
File file = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".jar");
assertThat(file).isFile();
@ -136,9 +136,8 @@ public class PackagingDocumentationTests {
@Test
public void bootJarIncludeLaunchScript() throws IOException {
this.gradleBuild
.script("src/main/gradle/packaging/boot-jar-include-launch-script.gradle")
.build("bootJar");
this.gradleBuild.script("src/main/gradle/packaging/boot-jar-include-launch-script"
+ this.dsl.getExtension()).build("bootJar");
File file = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".jar");
assertThat(file).isFile();
@ -148,8 +147,9 @@ public class PackagingDocumentationTests {
@Test
public void bootJarLaunchScriptProperties() throws IOException {
this.gradleBuild.script(
"src/main/gradle/packaging/boot-jar-launch-script-properties.gradle")
this.gradleBuild
.script("src/main/gradle/packaging/boot-jar-launch-script-properties"
+ this.dsl.getExtension())
.build("bootJar");
File file = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".jar");
@ -164,9 +164,8 @@ public class PackagingDocumentationTests {
"src/custom.script");
customScriptFile.getParentFile().mkdirs();
FileCopyUtils.copy("custom", new FileWriter(customScriptFile));
this.gradleBuild
.script("src/main/gradle/packaging/boot-jar-custom-launch-script.gradle")
.build("bootJar");
this.gradleBuild.script("src/main/gradle/packaging/boot-jar-custom-launch-script"
+ this.dsl.getExtension()).build("bootJar");
File file = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".jar");
assertThat(file).isFile();
@ -175,9 +174,8 @@ public class PackagingDocumentationTests {
@Test
public void bootWarPropertiesLauncher() throws IOException {
this.gradleBuild
.script("src/main/gradle/packaging/boot-war-properties-launcher.gradle")
.build("bootWar");
this.gradleBuild.script("src/main/gradle/packaging/boot-war-properties-launcher"
+ this.dsl.getExtension()).build("bootWar");
File file = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".war");
assertThat(file).isFile();
@ -188,8 +186,9 @@ public class PackagingDocumentationTests {
}
@Test
public void bootJarAndJar() throws IOException {
this.gradleBuild.script("src/main/gradle/packaging/boot-jar-and-jar.gradle")
public void bootJarAndJar() {
this.gradleBuild.script(
"src/main/gradle/packaging/boot-jar-and-jar" + this.dsl.getExtension())
.build("assemble");
File jar = new File(this.gradleBuild.getProjectDir(),
"build/libs/" + this.gradleBuild.getProjectDir().getName() + ".jar");

@ -20,6 +20,7 @@ import java.io.IOException;
import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.gradle.testkit.GradleBuild;
@ -29,26 +30,32 @@ import static org.assertj.core.api.Assertions.assertThat;
* Tests for the publishing documentation.
*
* @author Andy Wilkinson
* @author Jean-Baptiste Nizet
*/
@RunWith(GradleMultiDslSuite.class)
public class PublishingDocumentationTests {
@Rule
public GradleBuild gradleBuild = new GradleBuild();
public GradleBuild gradleBuild;
public DSL dsl;
@Test
public void mavenUpload() throws IOException {
assertThat(this.gradleBuild.script("src/main/gradle/publishing/maven.gradle")
assertThat(this.gradleBuild
.script("src/main/gradle/publishing/maven" + this.dsl.getExtension())
.build("deployerRepository").getOutput())
.contains("https://repo.example.com");
}
@Test
public void mavenPublish() throws IOException {
assertThat(
this.gradleBuild.script("src/main/gradle/publishing/maven-publish.gradle")
.build("publishingConfiguration").getOutput())
.contains("MavenPublication")
.contains("https://repo.example.com");
assertThat(this.gradleBuild
.script("src/main/gradle/publishing/maven-publish"
+ this.dsl.getExtension())
.build("publishingConfiguration").getOutput())
.contains("MavenPublication")
.contains("https://repo.example.com");
}
}

@ -21,6 +21,7 @@ import java.io.IOException;
import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.gradle.testkit.GradleBuild;
@ -30,23 +31,29 @@ import static org.assertj.core.api.Assertions.assertThat;
* Tests for the documentation about running a Spring Boot application.
*
* @author Andy Wilkinson
* @author Jean-Baptiste Nizet
*/
@RunWith(GradleMultiDslSuite.class)
public class RunningDocumentationTests {
@Rule
public GradleBuild gradleBuild = new GradleBuild();
public GradleBuild gradleBuild;
public DSL dsl;
@Test
public void bootRunMain() throws IOException {
assertThat(this.gradleBuild.script("src/main/gradle/running/boot-run-main.gradle")
assertThat(this.gradleBuild
.script("src/main/gradle/running/boot-run-main" + this.dsl.getExtension())
.build("configuredMainClass").getOutput())
.contains("com.example.ExampleApplication");
}
@Test
public void applicationPluginMainClassName() throws IOException {
assertThat(this.gradleBuild.script(
"src/main/gradle/running/application-plugin-main-class-name.gradle")
public void applicationPluginMainClassName() {
assertThat(this.gradleBuild
.script("src/main/gradle/running/application-plugin-main-class-name"
+ this.dsl.getExtension())
.build("configuredMainClass").getOutput())
.contains("com.example.ExampleApplication");
}
@ -54,7 +61,8 @@ public class RunningDocumentationTests {
@Test
public void springBootDslMainClassName() throws IOException {
assertThat(this.gradleBuild
.script("src/main/gradle/running/spring-boot-dsl-main-class-name.gradle")
.script("src/main/gradle/running/spring-boot-dsl-main-class-name"
+ this.dsl.getExtension())
.build("configuredMainClass").getOutput())
.contains("com.example.ExampleApplication");
}
@ -62,7 +70,8 @@ public class RunningDocumentationTests {
@Test
public void bootRunSourceResources() throws IOException {
assertThat(this.gradleBuild
.script("src/main/gradle/running/boot-run-source-resources.gradle")
.script("src/main/gradle/running/boot-run-source-resources"
+ this.dsl.getExtension())
.build("configuredClasspath").getOutput())
.contains(new File("src/main/resources").getPath());
}

@ -26,6 +26,7 @@ import java.util.Arrays;
import java.util.List;
import java.util.regex.Pattern;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.xpath.XPath;
import javax.xml.xpath.XPathExpression;
import javax.xml.xpath.XPathFactory;
@ -43,6 +44,9 @@ import org.junit.rules.TemporaryFolder;
import org.junit.rules.TestRule;
import org.junit.runner.Description;
import org.junit.runners.model.Statement;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;
import org.xml.sax.InputSource;
import org.springframework.asm.ClassVisitor;
@ -162,12 +166,19 @@ public class GradleBuild implements TestRule {
public GradleRunner prepareRunner(String... arguments) throws IOException {
String scriptContent = FileCopyUtils.copyToString(new FileReader(this.script))
.replace("{version}", getBootVersion());
.replace("{version}", getBootVersion())
.replace("{dependency-management-plugin-version}",
getDependencyManagementPluginVersion());
boolean isKotlin = this.script.endsWith(".kts");
String extension = isKotlin ? ".kts" : "";
FileCopyUtils.copy(scriptContent,
new FileWriter(new File(this.projectDir, "build.gradle")));
new FileWriter(new File(this.projectDir, "build.gradle" + extension)));
GradleRunner gradleRunner = GradleRunner.create().withProjectDir(this.projectDir)
.withDebug(true).withPluginClasspath(pluginClasspath());
.withPluginClasspath(pluginClasspath());
if (!isKotlin) {
// see https://github.com/gradle/gradle/issues/6862
gradleRunner.withDebug(true);
}
if (this.gradleVersion != null) {
gradleRunner.withGradleVersion(this.gradleVersion);
}
@ -191,6 +202,11 @@ public class GradleBuild implements TestRule {
return this;
}
public GradleBuild withMinimalGradleVersionForKotlinDSL() {
this.gradleVersion = "4.10.2";
return this;
}
public String getGradleVersion() {
return this.gradleVersion;
}
@ -201,13 +217,34 @@ public class GradleBuild implements TestRule {
+ "/text()");
}
private static String getDependencyManagementPluginVersion() {
try (FileReader pomReader = new FileReader(".flattened-pom.xml")) {
Document pom = DocumentBuilderFactory.newInstance().newDocumentBuilder()
.parse(new InputSource(pomReader));
NodeList dependencyElements = pom.getElementsByTagName("dependency");
for (int i = 0; i < dependencyElements.getLength(); i++) {
Element dependency = (Element) dependencyElements.item(i);
if (dependency.getElementsByTagName("artifactId").item(0).getTextContent()
.equals("dependency-management-plugin")) {
return dependency.getElementsByTagName("version").item(0)
.getTextContent();
}
}
throw new IllegalStateException(
"dependency management plugin version not found");
}
catch (Exception ex) {
throw new IllegalStateException(
"Failed to find dependency management plugin version", ex);
}
}
private static String evaluateExpression(String expression) {
try {
try (FileReader pomReader = new FileReader(".flattened-pom.xml")) {
XPathFactory xPathFactory = XPathFactory.newInstance();
XPath xpath = xPathFactory.newXPath();
XPathExpression expr = xpath.compile(expression);
String version = expr
.evaluate(new InputSource(new FileReader(".flattened-pom.xml")));
String version = expr.evaluate(new InputSource(pomReader));
return version;
}
catch (Exception ex) {

Loading…
Cancel
Save