If we want to execute a Java executable from a Gradle build, we have several options. Before we explore these options, we will first create a new Java class with a main()
method in our project. We will execute this Java class from our build file.
In the src/main/java/gradle/sample
directory, we need to create a new SampleApp.java
file. The following code listing shows the contents of the file. We will use our Sample
class to print the value of the getWelcomeMessage()
method to System.out
:
// File: src/main/java/gradle/sample/SampleApp.java package gradle.sample; public class SampleApp { public SampleApp() { } public static void main(String[] args) { final SampleApp app = new SampleApp(); app.welcomeMessage(); } public void welcomeMessage() { final String welcomeMessage = readMessage(); showMessage(welcomeMessage); } private String readMessage() { final Sample sample = new Sample(); final String message = sample.getWelcomeMessage(); return message; } private void showMessage(final String message) { System.out.println(message); } }
To run our SampleApp
class, we can use the javaexec()
method, which is part of Gradle's Project
class. We can also use the JavaExec
task in our build file. Finally, we can use the application plugin to run our SampleApp
class. In the next chapter, we will discuss how to use the javaexec
method.
The Project
class that is always available in our build file has the javaexec()
method. With this method, we can execute a Java class. The method accepts a closure that is used to configure the org.gradle.process.JavaExecSpec
object. JavaExecSpec
has several methods and properties that we can use to configure the main class that needs to be executed, optional arguments, and system properties. A lot of the options are same as the ones for running tests.
We will create a new build file and use the javaexec()
method to run our SampleApp
class with some extra options:
apply plugin: 'java' task runJava(dependsOn: classes, description: 'Run gradle.sample.SampleApp') << { javaexec { // Java main class to execute. main = 'gradle.sample.SampleApp' // We need to set the classpath. classpath sourceSets.main.runtimeClasspath // Extra options can be set. maxHeapSize = '128m' systemProperty 'sysProp', 'notUsed' jvmArgs '-client' } } repositories { jcenter() }
To run our Java class, we will execute the runJava
task from the command line and get the following output:
$ gradle runJava :compileJava :processResources :classes :runJava Welcome to Gradle. BUILD SUCCESSFUL Total time: 0.761 secs
Besides the javaexec()
method, we can define a new org.gradle.api.tasks.JavaExec
task. To configure the task, we can use the same methods and properties as with the javaexec()
method.
In the following sample build file, we will create the runJava
task of the JavaExec
type. We will configure the task to set the class path and main class. Also, we will see how to add other properties and invoke other methods to further configure the execution of the Java class, as follows:
apply plugin: 'java' task runJava(type: JavaExec) { dependsOn classes description = 'Run gradle.sample.SampleApp' // Java main class to execute. main = 'gradle.sample.SampleApp' // We need to set the classpath. classpath sourceSets.main.runtimeClasspath // Extra options can be set. systemProperty 'sysProp', 'notUsed' jvmArgs '-client' // We can pass arguments to the main() method // of gradle.sample.SampleApp. args 'mainMethodArgument', 'notUsed' }
If we run the task, we get the following output:
$ gradle runJava :compileJava UP-TO-DATE :processResources UP-TO-DATE :classes UP-TO-DATE :runJava Welcome to Gradle. BUILD SUCCESSFUL Total time: 0.686 secs
Another way to run a Java application is with the application plugin. The application plugin adds functionality to our build file in order to run Java applications and also to bundle the Java application for distribution.
To use the application plugin, we must add the plugin to our build file with the apply()
method. Once we have added the plugin, we can set the main class to be executed with the mainClassName
property. This time, we don't have to create a new task ourselves. The plugin has added the run
task that we can invoke to run the Java application.
The sample build file uses the application plugin to run our SampleApp
class, as follows:
apply plugin: 'application' mainClassName = 'gradle.sample.SampleApp' // Extra configuration for run task if needed. run { // Extra options can be set. systemProperty 'sysProp', 'notUsed' jvmArgs '-client' // We can pass arguments to the main() method // of gradle.sample.SampleApp. args 'mainMethodArgument', 'notUsed' }
We can invoke the run
task and check the output of the SampleApp
class:
$ gradle run :compileJava UP-TO-DATE :processResources UP-TO-DATE :classes UP-TO-DATE :run Welcome to Gradle. BUILD SUCCESSFUL Total time: 0.816 secs
Note that we don't have to set the classpath
property anymore. The plugin automatically includes the runtimeClasspath
object of the project to execute the Java class.
With the application plugin, we can also build a distribution with our Java application. This means that we can distribute the application, and people can run the Java application without Gradle. The plugin will create the necessary operating system-specific start scripts and package all the necessary classes and dependencies.
The following table shows the extra tasks that we can use with the application plugin to build a distribution:
Task |
Depends on |
Type |
Description |
|
|
|
This creates operating system-specific scripts to run the Java application |
|
|
|
This installs the application into a directory |
|
|
|
This creates a full distribution ZIP archive, including all the necessary files to run the Java application |
|
|
|
This creates a full distribution TAR archive, including all the necessary files to run the Java application |
All tasks depend on the Jar
task. In order to get a meaningful JAR filename, we set the archivesBaseName
and version
properties in our build file, as follows:
apply plugin: 'application' mainClassName = 'gradle.sample.SampleApp' archivesBaseName = 'gradle-sample' version = '1.0'
To create the start scripts, we invoke the createScript
task. After we have executed the task, we have two files, sample
and sample.bat
, in the build/scripts
directory. The sample.bat
file is for the Windows operating system and sample
is for other operating systems, such as Linux or OS X.
To have all files that are needed to run the application in a separate directory, we must run the installDist
task. When we execute the task, we get a sample
directory in the build/install
directory. The sample directory has a bin
directory with the start scripts and a lib
directory with the JAR file, containing the SampleApp
application. We can change to the build/install/sample
directory and then invoke bin/sample
or bin/sample.bat
to run our application:
$ gradle installDist :compileJava UP-TO-DATE :processResources UP-TO-DATE :classes UP-TO-DATE :jar UP-TO-DATE :startScripts UP-TO-DATE :installDist BUILD SUCCESSFUL Total time: 0.629 secs $ cd build/install/sample $ bin/sample Welcome to Gradle.
To create a ZIP archive with all the necessary files, which would enable others to run the application, we run the distZip
task. The resulting ZIP archive can be found in the build/distributions
directory. We can distribute this ZIP file and people can unzip the archive on their computers to run the Java application, as follows:
$ gradle distZip :compileJava UP-TO-DATE :processResources UP-TO-DATE :classes UP-TO-DATE :jar UP-TO-DATE :startScripts UP-TO-DATE :distZip BUILD SUCCESSFUL Total time: 0.602 secs $ jar tvf build/distributions/sample-1.0.zip 0 Wed Dec 16 10:23:42 CET 2015 app-1.0/ 0 Wed Dec 16 10:23:42 CET 2015 app-1.0/lib/ 2064 Wed Dec 16 10:18:54 CET 2015 app-1.0/lib/gradle-sample-1.0.jar 0 Wed Dec 16 10:23:42 CET 2015 app-1.0/bin/ 4874 Wed Dec 16 10:18:54 CET 2015 app-1.0/bin/sample 2329 Wed Dec 16 10:18:54 CET 2015 app-1.0/bin/sample.bat
To create a Tar archive, we use the distTar
task.
If we want to add other files to the distribution, we can create the src/dist
directory and place the files in there. Any files in the src/dist
directory are included in the distribution ZIP archive. To include files from another directory, we can use the applicationDistribution
copy specification.
The following sample build file uses the applicationDistribution
copy specification to include the output of the docs
task. Gradle will automatically execute the docs
task before invoking the distZip
task:
apply plugin: 'application' archivesBaseName = 'gradle-sample' version = '1.0' mainClassName = 'gradle.sample.SampleApp' task docs { ext { docsDir = 'docs' docsResultDir = file("$buildDir/$docsDir") } // Assign directory to task outputs. outputs.dir docsResultDir doLast { docsResultDir.mkdirs() new File(docsResultDir, 'README').write('Please read me.') } } applicationDistribution.from(docs) { // Directory in distribution ZIP archive. into 'docs' }
18.221.254.61