skip to content

installDist and Start Scripts

The bin/lib install layout and the generated cross-platform start scripts. Asked because it is how a JVM application ships when there is no container and no fat jar.

on this pageshow

questions

5

What does the installDist task produce, and what is the layout of its output directory?

level: juniorimportance: must knowfreq 60%

answer

  1. build/install/<name>/
  2. bin/ + lib/
  3. scripts + all runtime jars
  4. depends on jar + startScripts
  5. unpacked, runnable

basics

~10 s

installDist assembles a runnable, unpacked installation under build/install/<name>/ with two folders: bin/ holding the generated start scripts and lib/ holding the application jar plus all runtime dependency jars.

solid answer

~40 s

The Application plugin's `installDist` task creates an unpacked, ready-to-run image of your app on disk (no archiving). By default it lands in `build/install/<applicationName>/`. The layout is two directories: `bin/` contains the generated launcher scripts — `<name>` (a POSIX shell script) and `<name>.bat` (Windows) — produced by the `startScripts` task; `lib/` contains your project's jar plus every jar on the `runtimeClasspath`. The scripts build a classpath from everything in `lib/`, set `JAVA_OPTS`/`<APP>_OPTS`, locate the JVM via `JAVA_HOME` (falling back to `java` on PATH), and invoke your `mainClass`. Because it's unpacked, `installDist` is ideal for fast local smoke-testing of the packaged form before producing a `distZip`/`distTar`. It depends on `jar` and `startScripts`, so running it triggers a build of both.

code

bash · 5 lines
bash
./gradlew installDist
# build/install/myapp/
#   bin/myapp        bin/myapp.bat
#   lib/myapp-1.0.jar  lib/<deps>.jar
./build/install/myapp/bin/myapp --help

go deeper

for a junior

Name the location (build/install/<name>/) and the bin/ + lib/ split.

for a middle

Explain that lib/ holds the full runtimeClasspath and bin/ holds both POSIX and .bat launchers, plus the task dependency on jar and startScripts.

for a senior

Discuss using installDist for fast local smoke-tests of the packaged form, and how the scripts compose JAVA_OPTS / per-app OPTS / applicationDefaultJvmArgs.

for a principal

Frame installDist within a release pipeline: validate the unpacked image in CI before archiving, and standardize install layout across many service repos.

## What installDist is The **Application plugin** (`application`) gives you everything needed to run and package a JVM CLI/server app. One of its key tasks is **`installDist`**, which produces an *unpacked, runnable installation* of your application on the filesystem — as opposed to the archive tasks (`distZip`/`distTar`) which zip that same image. Think of `installDist` as "explode the distribution into a folder I can `cd` into and run". ## The output location By default the install lands in: ``` build/install/<applicationName>/ ``` `<applicationName>` defaults to the project name but is configurable via `application.applicationName`. ## The layout Inside that directory there are exactly two subdirectories: - **`bin/`** — the generated **start scripts**, produced by the `startScripts` task (type `CreateStartScripts`). You get two files: `<name>` (a Bourne/POSIX shell launcher for Linux/macOS) and `<name>.bat` (a Windows batch launcher). - **`lib/`** — every jar needed at runtime: your project's own jar **plus** all jars resolved from the `runtimeClasspath` configuration (your dependencies). ``` build/install/myapp/ ├── bin/ │ ├── myapp │ └── myapp.bat └── lib/ ├── myapp-1.0.jar ├── guava-33.0.jar └── ... ``` ## How the scripts run the app The generated launcher: 1. Computes the install root from its own location. 2. Builds a classpath listing each jar under `lib/`. 3. Reads `JAVA_OPTS` and a per-app `<APP_NAME>_OPTS` env var (plus any baked-in `applicationDefaultJvmArgs`). 4. Finds the JVM via `JAVA_HOME` or `java` on the `PATH`. 5. Executes `java -cp <lib jars> <mainClass> "$@"`. ## Task wiring `installDist` depends on `jar` (to build your jar) and `startScripts` (to generate `bin/`). Running `./gradlew installDist` builds all three. There is also an `installDist`-style `run` task for in-place execution, but `installDist` specifically materializes the on-disk image — useful to smoke-test the exact thing a user will unzip.

  • What populates the lib/ directory?
    Your project's jar plus everything on the runtimeClasspath configuration — i.e., all runtime dependency jars, not just direct ones.
  • How is installDist different from distZip?
    distZip archives the same image into a .zip; installDist leaves it unpacked on disk so you can run it directly without extracting.

installDist is like unzipping the shipping box onto your desk so you can use the product immediately, whereas distZip is the sealed box you mail to a customer.

saying these in an interview costs you the question

  • Saying installDist produces a single fat jar — it does not; it produces a folder with separate jars in lib/.
  • Claiming the output is build/libs — that's the jar task; installDist outputs under build/install/.

context

open as a page

What is the CreateStartScripts task type, and what does the generated launcher script actually do at runtime?

level: middleimportance: must knowfreq 50%

basics

~10 s

CreateStartScripts is the task type behind the startScripts task. It generates the bin/<name> (Unix) and bin/<name>.bat (Windows) launchers that build the classpath from lib/, locate the JVM, apply JVM options, and run your mainClass.

open as a page

How does applicationName affect installDist, and how do you change the name of the install directory and the launcher executables?

level: middleimportance: should knowfreq 35%

basics

~10 s

applicationName (set in the application { } block) drives the install folder name (build/install/<applicationName>/) and the base names of the generated scripts (bin/<applicationName> and bin/<applicationName>.bat). It defaults to the project name.

open as a page

What is executableDir in the Application plugin, and how does it change the location of the start scripts within an install?

level: seniorimportance: should knowfreq 25%

basics

~20 s

executableDir is the relative path inside the distribution where the launcher scripts are placed; it defaults to "bin". Setting it (e.g. "runtime/bin") moves the scripts there, while the scripts still resolve the app home relative to their own location.

open as a page

When would you use installDist for local verification, and how does it relate to the run task and the archive tasks?

level: seniorimportance: should knowfreq 30%

basics

~20 s

installDist materializes the exact unpacked distribution (bin/ + lib/) on disk so you can launch it via its real start script — closer to production than the run task, and faster to iterate than building and extracting distZip/distTar.

open as a page