What is a .jmod file and how does it differ from a regular JAR, and when do you need jmod?
answer
- .jmod = richer module package: native libs, cmds, config, headers, legal
- Link-time/compile-time only — NOT runnable via java -m
- JDK platform modules ship as .jmod (see $JAVA_HOME/jmods)
- Modular JAR is runnable directly AND feeds jlink
- jmod subcommands: create / list / describe / extract / hash
basics
~20 sA .jmod file is a packaging format for a module that, unlike a JAR, can also carry native libraries, native commands, config files, and legal/header files. You create and inspect .jmod files with the jmod tool. They are used at link time (by jlink), not at application runtime.
solid answer
~50 sjmod is the JDK tool for creating and inspecting .jmod files. A .jmod is a module package format that goes beyond a JAR: besides classes and module-info, it can bundle native libraries (--libs), native commands (--cmds), config files (--config), header files, man pages, and legal notices. That's why the JDK's own platform modules ship as .jmod files. The crucial distinction: .jmod files are consumable only at compile and link time — notably by jlink when assembling a runtime image — they cannot be placed on the runtime module path and run directly with java -m. So you reach for jmod when a module needs to carry native code or extra resources that a JAR can't represent, or when authoring modules that feed jlink. For ordinary application modules with no native bits, a modular JAR is simpler and is what you run.
code
java · 15 lines// Create a .jmod that bundles classes AND native libraries:
// jmod create \
// --class-path out/classes \
// --libs native/linux-x64 \
// --cmds bin/ \
// mylib.jmod
//
// Inspect it:
// jmod describe mylib.jmod # prints requires/exports
// jmod list mylib.jmod # lists all entries
//
// Then feed it to jlink (link-time use):
// jlink --module-path "$JAVA_HOME/jmods:." --add-modules my.lib --output image
//
// NOTE: `java --module-path mylib.jmod -m my.lib/...` will NOT work — .jmod is link-time only.go deeper
Knows .jmod is another way to package a module and that jmod is the tool that makes them.
Can explain that .jmod carries native libs/config beyond a JAR and that it's used at link time, and can run jmod describe/list to inspect one.
Articulates the link-time-only constraint, the modular-JAR-vs-.jmod decision rule, why platform modules are .jmod, and uses jmod create with --libs/--cmds for native-bearing modules.
Designs packaging strategy for modules with native dependencies across platforms, decides where .jmod vs modular JAR vs native bundling fits the release pipeline, and reasons about jmod hash for integrity in a custom runtime supply chain.
## The two module packaging formats Since Java 9 a module can be delivered in two on-disk forms: 1. **Modular JAR**: an ordinary `.jar` (a ZIP of class files and resources) that *also* contains a `module-info.class` at its root. It is the everyday format — you can put it on the **module path** and run it directly: `java --module-path libs -m your.module/your.Main`. 2. **`.jmod` file**: a newer package format produced by the **jmod** tool. It is also a ZIP-like container, but it can hold things a JAR cannot meaningfully package. ## What a .jmod can carry that a JAR can't A `.jmod` has named sections, populated by jmod options: - **classes** (`--class-path`): the bytecode + `module-info`. - **native libraries** (`--libs`): platform `.so`/`.dll`/`.dylib` files the module needs. - **native commands** (`--cmds`): executables to place in the image's `bin/`. - **config** (`--config`): configuration files. - **header files** (`--header-files`), **man pages** (`--man-pages`), **legal notices** (`--legal-notices`). This richer structure is exactly why **the JDK's own platform modules ship as `.jmod` files** (look in `$JAVA_HOME/jmods/`): the platform needs to bundle native code and tooling, not just classes. ## The decisive difference: link-time only The single most important fact: **`.jmod` files are usable only at compile time and link time — not at run time.** You **cannot** put a `.jmod` on the runtime module path and launch it with `java -m`. Their purpose is to be inputs to **jlink**, which assembles them (and the platform `.jmod`s) into a runtime image. A **modular JAR**, by contrast, is runnable directly *and* can also feed jlink. So the decision rule: - Plain application module, JVM bytecode + resources only → **modular JAR** (simpler, directly runnable). - Module that must bundle **native libraries, native commands, or extra config/man/legal artifacts**, or that you are authoring specifically to feed a custom jlink image → **`.jmod`**. ## Using the jmod tool jmod has subcommands: - `jmod create --class-path classes/ --libs native/ mymod.jmod` — build a .jmod. - `jmod list mymod.jmod` — list its contents. - `jmod describe mymod.jmod` — print the module descriptor (requires/exports). - `jmod extract` — unpack it. - `jmod hash` — record dependency hashes for tamper/version checks. ## How it fits the toolchain Think of the JPMS tooling as a pipeline: **jdeps** analyzes what you depend on and can draft a `module-info`; **jmod** packages a module (including native bits) into a `.jmod`; **jlink** links `.jmod`/modular-JAR inputs into a minimal runtime image. Most application developers touch jdeps and jlink often and jmod rarely — jmod matters mainly when native code or platform-style packaging is involved.
- Why can't you run a .jmod file directly with java -m?By design, .jmod is a compile-time/link-time format. The runtime module system only loads from the module path as modular JARs (or exploded modules) or from the linked image; .jmod files are meant to be inputs to jlink, not loaded at runtime.
- Why do the JDK's own platform modules ship as .jmod rather than JARs?Platform modules bundle native libraries and native commands (and headers/legal files) that a JAR can't package; .jmod's richer sections accommodate them, and they're linked into images by jlink.
- When would an application developer realistically create a .jmod?When a module must bundle its own native libraries or commands, or when authoring modules explicitly to feed a custom jlink runtime image with non-class artifacts. For pure-bytecode modules a modular JAR suffices.
saying these in an interview costs you the question
- Saying you can run a .jmod directly with java -m — you cannot; it's link-time only
- Treating .jmod as just a renamed JAR — it carries native libs/cmds/config a JAR can't
- Believing every module must be a .jmod to use jlink — modular JARs work too
- Confusing jmod (packaging) with jlink (image assembly)