install4j 11.0 introduces the following notable new features:
macOS notarization is now cross-platform. Previously, notarization required macOS, either for building or for manual post-processing.
From install4j 11 onwards, install4j can perform the notarization process on any platform.
This allows install4j builds to be fully cross-platform.
The App Store Connect API required for notarization operations is now configured with the issuer ID, the key ID and the private API key that
are obtained from App Store Connect.
PKCS #11 code signing improvements. The PKCS #11 implementation has been rewritten from scratch without the use of the SunPKCS11 Java
Security Provider. This enables the implementation of more features for PKCS #11 and provides better error messages in case of configuration
problems.
In this release, we added a selection dialog for the PKCS #11 slot index that lists HSM descriptions and manufacturers. This is
important if you have multiple HSMs.
In install4j 11, you can now select a certificate by its label, as well as by its issuer and serial number
Also, if you leave the certificate selection empty, install4j will automatically select the code signing certificate with the longest
validity period.
Up to install4j 11, PKCS #11 was only available for Windows code signing. Now there is a PKCS #11 option for macOS code signing as well.
Windows code signing has been improved. Instead of configuring a code signing executable in the "Executable processing" step
in the media wizard for all Windows media files, you can now configure an executable like Azure Sign Tool
on the "General Settings → Code Signing" step. The command is called for each executable that has to be signed including the
generated launchers.
With the chained certificates directory, it is now possible to tell install4j about intermediate certificates that need to be taken
into account for code signing to establish the complete hierarchy of trust.
Major improvements in the script editor. When developing an installer with install4j, you usually make extensive use of the script editor.
Although the script editor previously included code completion and problem detection, it lacked many features that you
would expect from a modern IDE. In install4j 11, we implemented a lot of functionality to boost your productivity with install4j.
Caret highlights have been implemented in the script editor. Read and write access have different background colors, and the right
gutter shows occurrences that can be navigated to by clicking on them.
Code completion has been improved. It now suggests automatically as you type by default. You can disable this behavior in the
Java editor settings dialog.
There are now a number of templates that are tab-expandable for common code snippets, such as printing to
stderr with "serr", as shown in the screenshot below. Other snippets, for example, are "log" to write to the log file and "ex" to log an
exception.
Also, all static methods in install4j API classes are suggested without having to first type the class name. In that way, you can start with a
method name and install4j will add the static import for the class automatically.
An action to rename variables has been added (Code → Rename).
A new action allows you to reformat the entire script or selected code (Code → Reformat Code).
Reformatting is done according to the Eclipse default Java formatting style. If you would like to use custom formatting settings,
you can export a single Eclipse profile and specify it in the Java editor settings. Exporting Eclipse XML profile files is supported by
Eclipse, IntelliJ IDEA and the RedHat Java plugin of VS Code. The tab size used for editing and reformatting is directly configurable
in the Java editor settings.
Also, typing a closing brace now reformats the preceding block. This behavior can be disabled in the Java editor settings.
An action to optimize the imports for the current script has been added (Code → Optimize Imports).
An action to show the available parameters for all overloaded methods of the method call at the caret has been added
(Code → Parameter Info). It highlights the matched arguments up to caret and selects the overloaded variant chosen during
code completion if possible.
Actions to navigate between problems have been added to the script editor. Problems are either warnings or errors and can be shown
by hovering over the underlined text or the indicator in the right gutter.
Selecting code blocks is now possible with the new "Extend selection" and "Shrink selection" actions. Repeated invocations of those
actions select surrounding or contained blocks of code around the current caret position.
The script editor now has support for quick fixes. If the caret is on a detected problem, a floating popup with a lightbulb or the
Code → Quick Fix action will show a context menu with automatic modifications that will resolve the problem. The list of available quick fixes
include:
- Remove unused, duplicate, conflicting or non-existent imports
- Import ambiguous or unresolved types
- Fix unterminated strings
- Fix type mismatches
- Fix wrong return statements
- Fix instance access to static members
- Fix wrong visibilities and method modifiers in overrides
- Fix abstract modifier problems
- Implement unimplemented methods
- Create local unresolved variable
- Remove unused local variables
- Remove dead code
- Remove casts
An new action has been introduced to refactor code (Code → Refactor). When invoked, a popup with applicable refactorings for the current
caret position is shown. The list of available refactorings include:
- Extract to local variable
- Inline local variable
- Convert to lambda expression
- Convert to anonymous class creation
- Convert var to an explicit type and vice versa
- Convert to static import
- Surround with try/catch
- Convert to enhanced for loop
- Add inferred lambda parameter type
- Replace lambda parameter types with var
- Change lambda body expression to block
- Change body block to expression
- Remove lambda parameter types
- Convert lambda to method reference
- Use MessageFormat for string concatenation
- Use StringBuilder for string concatenation
- Use "String.format" for string concatenation
- Convert String concatenation to text block
- Convert to switch expression
- Split variable declaration
- Join variable declaration
- Invert equals comparison
Alternative keymaps for popular IDEs are now supported by the script editor. When first using the script editor, install4j will ask you
to choose an initial keymap.
You can change the keymap or customize it at any later time by invoking Settings → Keymap in the Java editor settings.
install4j 11 delivers several important improvements for compiler variables. Compiler variables are used to define values that are
used in multiple places in the project and to customize the project externally from your build system.
Compiler variables can be now declared to contain sensitive information. In that case, their value is not written to the runtime
configuration and cannot be retrieved via context.getCompilerVariable("variableName")
. You can still use the compiler variable
in all text fields with the ${compiler:variableName}
syntax because these usages are replaced at build time.
Platform-specific overrides for compiler variables were added. While it was always possible to override compiler variable values for
media files, it was inconvenient when the overriding value was always identical for the same platform. Now, you can override for Windows,
macOS and Linux/Unix. These overrides can be further refined with the media-specific overrides.
You can now refer to the base value when overriding a compiler variable with the syntax ${compiler:variableName}
. This
applies to both platform-specific and media-specific overrides. There are many related use cases, for example, a list of VM parameters with
common values and additional values for each platform. Previously, you would have had to introduce a separate compiler variable for the
additional value.
File and path separators can be converted to the build or the target platform. This means you do not have to repeatedly use the
compiler variables sys.fileSeparator
, sys.pathlistSeparator
, sys.mediaFileSeparator
or
sys.mediaPathlistSeparator
anymore. Instead, you can use either Unix-style ('/' and ':') or Windows-style ('\' and ';') file
and path separators in the value. Both styles are converted in the same way.
This feature has also been implemented for pre-defined installer variables of type String.
Actions to read and modify JSON files were added. The mechanism to select parts of a JSON document that should be read or modified is
the JSONPath expression. JSON actions use the
Jayway JsonPath library. A shadowed copy of this library is only bundled with the
installer if at least one JSON action is used in your project.
The "Read value from a JSON file" action saves the match of the JSONPath to the specified variable. Depending on the JSONPath
expression, the variable is either a primitive value, an instance of java.util.List
for array matches, or an instance of
java.util.Map
for object matches.
The "Count occurrences in a JSON file" action counts the number of matches of the JSONPath and saves the result to the specified
variable. In this case, the JSONPath expression should be an indefinite expression.
Finally, the "Modify JSON files" action replaces the matches of a JSONPath expression in one or multiple files. You
can choose to
- Set values
- Replace values
- Add to arrays
- Delete values
- Add or update object keys
- Rename object keys
by adjusting the "Modification type" property and filling out its child properties.
Support for symlinks has been improved. The "Copy files and directories" and "Move files and directories" actions now fully support
symlinks. Their "Symlink handling" property controls whether the content is copied or whether the same relative or absolute target should
be used. The "On symlink creation failure" property offers different failure strategies during symlink handling.
The "Create a symbolic link" action now also supports Windows. Execution on Windows is controlled by the "Execute on Windows" property
and is disabled by default.
The support for reusing the installed JRE in update installers was improved.
There is now a "Previous installations" search sequence entry type under "General Settings → JRE Bundles → Search Sequence"
that allows you to reuse the installed JRE in update installers. Only installations with the same application ID are considered.
If a JRE was found in that way, the "Install files" action now copies that JRE from a different installation to the current installation
directory. This prevents problems that would otherwise occur when the previous installation is uninstalled.
Update downloaders can now make decisions based on the Java version of the update installer by inspecting
com.install4j.api.update.UpdateDescriptorEntry#getJreMinVersion
and #getJreMaxVersion
.
In that way, you can choose to download an update installer without a bundled JRE if you can determine that the requirements for the JRE
have not changed. Other attributes in the update descriptor can also be used for this purpose. These attributes are configurable under
"Installer → Auto Update Options".
The initial progress dialog of Windows installers now supports dark mode. In those cases where the installer will be shown in dark mode,
the initial progress dialog will also have a dark theme. This is a native dialog and so its styling slightly differs from the main installer
window.
This feature works for Windows 11 and higher.
Installers are now localized into Ukrainian.
Localizations are configured under "General Settings → Languages".
The options presented to the user in case of action failures are now more flexible.
The "Ask user" failure strategy for actions and action groups now has separate sub-options for allowing "Retry", "Ignore" and "Quit"
answers from the user. Previously there were only limited fixed combinations.
The selection script of several form components is now more flexible.
The "Checkbox", "Single radio button" and "Radio button group" form components received an "Also execute when screen is activated" property
as a child property of the "Selection script" property for cases where the script manages the visibility or enablement of other form
components.
Multi-line labels can be made selectable.
The "Multi-line label" and the "Multi-line HTML label" form components have received a "Make text selectable" property so that the user
can select text with the mouse and copy it to the clipboard.
Gradle, Maven, and Ant plugins can now auto-provision the appropriate version of install4j.
Specifying the "installDir" parameter is still possible, but no longer required.
Here's an example of a minimal Gradle script that builds an installer with install4j 11.0:
import com.install4j.gradle.Install4jTask
plugins {
id("com.install4j.gradle") version "11.0"
}
tasks.register<Install4jTask>("media") {
projectFile = file("hello.install4j")
}
A Maven POM to compile an installer will look like this:
<project>
<modelVersion>4.0.0</modelVersion>
<groupId>com.test.hello</groupId>
<artifactId>hello-world</artifactId>
<version>1.0</version>
<pluginRepositories>
<pluginRepository>
<id>ej-technologies</id>
<url>https://maven.ej-technologies.com/repository</url>
</pluginRepository>
</pluginRepositories>
<build>
<plugins>
<plugin>
<groupId>com.install4j</groupId>
<artifactId>install4j-maven</artifactId>
<version>11.0</version>
<executions>
<execution>
<goals>
<goal>compile</goal>
</goals>
<configuration>
<projectFile>${project.basedir}/hello.install4j</projectFile>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
The earlier method of specifying the "installDir" property remains available.
The Gradle plugin now works with the configuration cache.
To check whether media files are up to date, the Gradle task would need to determine the list of input files.
Because the plugin cannot do that without invoking the compiler, the install4j task is never up to date and is always executed.
Starting with 11.0, if you define your own file inputs on the task, the up-to-date check is enabled.
You can track input files with calls like
...
inputs.dir(stagingDir)
inputs.files(file1, file2)
...
in the task definition.
To support the configuration cache, we had to migrate all properties to Gradle providers. This means that the binary interface of the
tasks has changed and you will likely have to adjust your build script.