io7m | single-page | multi-page | epub | Montarre User Manual 0.0.3
Front Matter
Front Matter
2. Installation
1
The montarre package provides tools for producing platform-specific native executables and installation media from a single platform-independent source package.
1
In traditional programming environments, prior to Java, compilers typically produced native code for the platform upon which they were running. If you were on hardware architecture A, using operating system O, then unless you were willing to go through the pain and suffering of configuring a cross-compiler, you could only produce native executables that would run on hardware architecture A, using operating system O.
2
As a consequence of this, if you wanted to distribute a program for a range of hardware architectures and operating systems, you would have to maintain at most M * N systems to build code (where M is the number of operating systems and N is the number of hardware architectures). Worse, all of these systems had to be trusted to actually produce code that was correct given a single package of source code. Even worse, because each platform would inevitably have its own set of tools, the singled shared build procedure for the code would become exponentially complicated with lots of branching logic in order to get it to run correctly on all platforms [1].
4
Java, with varying degrees of success, opted to follow a write once run anywhere paradigm: The output of the compiler is platform-neutral bytecode, and end-consumers would simply load this bytecode into their locally installed Java Virtual Machine. It therefore wouldn't matter on what hardware architecture and/or on which operating system the code was compiled, as the output of the process would ostensibly be the same regardless. This would essentially collapse the above diagram to one that looked like this:
6
This was theoretically absolutely ideal from a developer perspective. A developer could maintain a single machine and use it to produce code for any number of completely different platforms. The developer could offer a single download link online for the program instead of having to offer one per platform.
7
In practice, there were some issues with this. Using the above system, it is not possible to know ahead of time which version of the Java VM is installed on end-user systems. Java bytecode is versioned, and a given Java VM has a stated upper bound on the bytecode versions it can support. If a user has a Java 21 VM installed, and is given Java bytecode targeting Java 23, the bytecode will simply not run. Worse, on many operating systems, the Java VM will print an error message about the bytecode version, but the desktop environment will simply hide/discard the message. This leaves users with silently failing programs.
8
In Java 14, the jpackage tool was introduced. The jpackage tool can be handed Java bytecode, and a Java VM, and the tool will produce a native executable for the current platform that runs the given bytecode. This is both a benefit and a curse; a benefit because it is now possible to package Java code in a manner that makes it immune to the problem of not having a suitable Java VM installed, but a curse because it could indicate somewhat of a return to the N by M compilation model.
9
Let's consider what might be an ideal build setup that would keep our nice, simple, straightforward platform-neutral builds, but would also be able to produce platform-specific artifacts on demand without introducing any complexity into the build.
10
In an ideal world, we would have our Java compilation process stay completely platform-independent, and produce identical results regardless of the platform upon which it is run. The output of this process would be a completely platform-neutral artifact that a user could theoretically run if they had an appropriate runtime installed. The platform-neutral artifact could be signed, published and that would be the end of it from the perspective of our build system.
11
We would then like a second process, completely isolated and decoupled from the first, where that platform-independent artifact could be downloaded from a repository and transformed into something more familiar and suitable for the platform upon which it is running. Ideally, the second process would leave the bytecode of the original platform-independent artifact completely intact so that we could trust that the code is still "correct" and hasn't been broken in some platform-specific way. The jpackage tool can achieve this, but requires a lot of per-platform configuration in order to get good results. In practice, the jpackage tool really requires knowledge of your original build process as it will not otherwise have all the information it needs to, for example, categorize any platform-dependent native libraries included in the original artifact, or have access to other metadata such as license information.
13
The montarre package attempts to provide tools to achieve the above in relatively painless manner. It attempts to adhere to a paradigm of compile once, transform anywhere!
1
The montarre package provides the following features:

1.3.2. Features

  • A rich, strictly-defined, and well-specified packaging format that remains platform-independent whilst allowing straightforward zero-configuration transformations to a wide range of platform-specific package formats.
  • Extensive, type-driven, ahead-of-time checking; if your package validates, you should get working native packages on all platforms.
  • Reproducible builds by default.
  • Support for producing simple jpackage "app-image" executables on any platform.
  • Support for producing Debian .deb packages.
  • Support for producing Windows MSI installers.
  • Support for producing Flatpaks.
  • A carefully-engineered Java API for creating, manipulating, and transforming packages.
  • A full command-line interface built on top of the Java API.
  • A Maven plugin for producing packages from any Maven module.

Footnotes

1
See practically any C or C++ project written in the past thirty years for examples of just how bad this can get.
References to this footnote: 1
Front Matter
Front Matter
2. Installation
io7m | single-page | multi-page | epub | Montarre User Manual 0.0.3