Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
31 commits
Select commit Hold shift + click to select a range
12d034f
8361224: [macos] MacSignTest.testMultipleCertificates failed
Jul 14, 2025
2886454
8351073: [macos] jpackage produces invalid Java runtime DMG bundles
Jul 18, 2025
b44d8cf
8360507: JPKG002-006: SigningPackageTest: appOutput.txt cannot be fou…
Jul 28, 2025
631938a
8362352: Fix references to non-existing resource strings
Aug 5, 2025
3cb207f
8359756: Bug in RuntimePackageTest.testName test
Aug 5, 2025
c140a9a
8364587: Update jpackage internal javadoc
Aug 5, 2025
222bbae
8364564: Shortcut configuration is not recorded in .jpackage.xml file
Aug 8, 2025
57652f2
8308349: missing working directory option for launcher when invoked f…
Aug 12, 2025
4ec4e6b
8365555: Cleanup redundancies in jpackage implementation
Aug 16, 2025
0c0ab80
8356218: [macos] Document --app-content
Aug 22, 2025
c319bc4
8362335: [macos] Change value of CFBundleDevelopmentRegion from "Engl…
Aug 28, 2025
4273389
8343221: IOUtils.copyRecursive() doesn't create parent directories
Sep 22, 2025
20b830b
8368030: Make package bundlers stateless
Sep 26, 2025
038c043
8362598: [macos] Add tests for custom info plist files
Oct 10, 2025
8667371
8356047: [macos] jpackage produces confusing post- and pre- installat…
Oct 10, 2025
1a557a4
8363979: Add JDK bundle/image validation for --runtime-image option
Oct 10, 2025
5698e21
8356575: Test order in which jpackage fills app image
Oct 17, 2025
32df2ad
8370134: Fix minor jpackage issues
Oct 18, 2025
c4da029
8370120: Make jpackage tests output more stable
Oct 18, 2025
356c183
8370136: Support async execution of jpackage tests
Oct 21, 2025
094fbd9
8370123: Minor jpackage refactoring
Oct 21, 2025
b0af8de
8370126: Improve jpackage signing testing
Oct 21, 2025
1ec2b52
8356578: Test --mac-entitlements
Oct 21, 2025
60c9f08
8370122: jpackage test lib improvements
Oct 22, 2025
13ffd9a
8370442: Compilation error in jpackage EntitlementsTest test
Oct 22, 2025
c476293
8370156: Fix jpackage IconTest
Oct 22, 2025
b567993
8343220: Add test cases to AppContentTest jpackage test
Oct 24, 2025
855a964
8370100: Redundant .png files in Linux app-image cause unnecessary bloat
Oct 28, 2025
561ffb3
8370956: ShortcutHintTest test fails when executed locally on Linux
Oct 30, 2025
9c1a1bb
8370969: --launcher-as-service option is ignored when used with --app…
Nov 1, 2025
049c546
8371076: jpackage will wrongly overwrite the plist file in the embedd…
Nov 2, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -24,10 +24,9 @@
*/
package jdk.jpackage.internal;

import jdk.jpackage.internal.model.LinuxPackage;
import jdk.jpackage.internal.model.LinuxLauncher;
import jdk.jpackage.internal.model.Package;
import jdk.jpackage.internal.model.Launcher;
import static jdk.jpackage.internal.ApplicationImageUtils.createLauncherIconResource;
import static jdk.jpackage.internal.model.LauncherShortcut.toRequest;

import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
Expand All @@ -45,12 +44,14 @@
import javax.imageio.ImageIO;
import javax.xml.stream.XMLStreamException;
import javax.xml.stream.XMLStreamWriter;
import static jdk.jpackage.internal.ApplicationImageUtils.createLauncherIconResource;
import jdk.jpackage.internal.model.FileAssociation;
import jdk.jpackage.internal.model.LauncherShortcut;
import jdk.jpackage.internal.model.LinuxLauncher;
import jdk.jpackage.internal.model.LinuxPackage;
import jdk.jpackage.internal.model.Package;
import jdk.jpackage.internal.util.CompositeProxy;
import jdk.jpackage.internal.util.PathUtils;
import jdk.jpackage.internal.util.XmlUtils;
import static jdk.jpackage.internal.util.function.ThrowingFunction.toFunction;

/**
* Helper to create files for desktop integration.
Expand All @@ -65,7 +66,7 @@ final class DesktopIntegration extends ShellCustomAction {
private static final List<String> REPLACEMENT_STRING_IDS = List.of(
COMMANDS_INSTALL, COMMANDS_UNINSTALL, SCRIPTS, COMMON_SCRIPTS);

private DesktopIntegration(BuildEnv env, LinuxPackage pkg, LinuxLauncher launcher) throws IOException {
private DesktopIntegration(BuildEnv env, LinuxPackage pkg, LinuxLauncher launcher) {

associations = launcher.fileAssociations().stream().map(
LinuxFileAssociation::create).toList();
Expand All @@ -77,20 +78,14 @@ private DesktopIntegration(BuildEnv env, LinuxPackage pkg, LinuxLauncher launche
// Need desktop and icon files if one of conditions is met:
// - there are file associations configured
// - user explicitly requested to create a shortcut
boolean withDesktopFile = !associations.isEmpty() || launcher.shortcut().orElse(false);

var curIconResource = createLauncherIconResource(pkg.app(), launcher,
env::createResource);
boolean withDesktopFile = !associations.isEmpty() || toRequest(launcher.shortcut()).orElse(false);

if (curIconResource.isEmpty()) {
if (!launcher.hasIcon()) {
// This is additional launcher with explicit `no icon` configuration.
withDesktopFile = false;
} else {
final Path nullPath = null;
if (curIconResource.get().saveToFile(nullPath) != OverridableResource.Source.DefaultResource) {
// This launcher has custom icon configured.
withDesktopFile = true;
}
} else if (launcher.hasCustomIcon()) {
// This launcher has custom icon configured.
withDesktopFile = true;
}

desktopFileResource = env.createResource("template.desktop")
Expand All @@ -112,17 +107,12 @@ private DesktopIntegration(BuildEnv env, LinuxPackage pkg, LinuxLauncher launche
if (withDesktopFile) {
desktopFile = Optional.of(createDesktopFile(desktopFileName));
iconFile = Optional.of(createDesktopFile(escapedAppFileName + ".png"));

if (curIconResource.isEmpty()) {
// Create default icon.
curIconResource = createLauncherIconResource(pkg.app(), pkg.app().mainLauncher().orElseThrow(), env::createResource);
}
} else {
desktopFile = Optional.empty();
iconFile = Optional.empty();
}

iconResource = curIconResource;
iconResource = createLauncherIconResource(launcher, env::createResource);

desktopFileData = createDataForDesktopFile();

Expand All @@ -132,14 +122,14 @@ private DesktopIntegration(BuildEnv env, LinuxPackage pkg, LinuxLauncher launche
nestedIntegrations = pkg.app().additionalLaunchers().stream().map(v -> {
return (LinuxLauncher)v;
}).filter(l -> {
return l.shortcut().orElse(true);
}).map(toFunction(l -> {
return toRequest(l.shortcut()).orElse(true);
}).map(l -> {
return new DesktopIntegration(env, pkg, l);
})).toList();
}).toList();
}
}

static ShellCustomAction create(BuildEnv env, Package pkg) throws IOException {
static ShellCustomAction create(BuildEnv env, Package pkg) {
if (pkg.isRuntimeInstaller()) {
return ShellCustomAction.nop(REPLACEMENT_STRING_IDS);
}
Expand Down Expand Up @@ -225,15 +215,34 @@ private List<String> requiredPackagesSelf() {
}

private Map<String, String> createDataForDesktopFile() {

var installedLayout = pkg.asInstalledPackageApplicationLayout().orElseThrow();

Map<String, String> data = new HashMap<>();
data.put("APPLICATION_NAME", launcher.name());
data.put("APPLICATION_DESCRIPTION", launcher.description());
data.put("APPLICATION_ICON", iconFile.map(
f -> f.installPath().toString()).orElse(null));
data.put("DEPLOY_BUNDLE_CATEGORY", pkg.menuGroupName());
data.put("APPLICATION_LAUNCHER", Enquoter.forPropertyValues().applyTo(
pkg.asInstalledPackageApplicationLayout().orElseThrow().launchersDirectory().resolve(
launcher.executableNameWithSuffix()).toString()));
installedLayout.launchersDirectory().resolve(launcher.executableNameWithSuffix()).toString()));
data.put("STARTUP_DIRECTORY", launcher.shortcut()
.flatMap(LauncherShortcut::startupDirectory)
.map(startupDirectory -> {
switch (startupDirectory) {
case DEFAULT -> {
return (Path)null;
}
case APP_DIR -> {
return installedLayout.appDirectory();
}
default -> {
throw new AssertionError();
}
}
}).map(str -> {
return "Path=" + str;
}).orElse(null));

return data;
}
Expand Down Expand Up @@ -334,7 +343,7 @@ void applyTo(Map<String, String> data) {
* - installPath(): path where it should be installed by package manager;
*/
private InstallableFile createDesktopFile(String fileName) {
var srcPath = pkg.asPackageApplicationLayout().orElseThrow().resolveAt(env.appImageDir()).desktopIntegrationDirectory().resolve(fileName);
var srcPath = env.asApplicationLayout().orElseThrow().desktopIntegrationDirectory().resolve(fileName);
var installPath = pkg.asInstalledPackageApplicationLayout().orElseThrow().desktopIntegrationDirectory().resolve(fileName);
return new InstallableFile(srcPath, installPath);
}
Expand Down Expand Up @@ -481,7 +490,7 @@ private static int getIconSize(FileAssociation fa) {

private final BuildEnv env;
private final LinuxPackage pkg;
private final Launcher launcher;
private final LinuxLauncher launcher;

private final List<LinuxFileAssociation> associations;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,13 +25,15 @@

package jdk.jpackage.internal;

import java.util.Optional;

public class LinuxAppBundler extends AppImageBundler {
public LinuxAppBundler() {
setAppImageSupplier((params, output) -> {
// Order is important!
var app = LinuxFromParams.APPLICATION.fetchFrom(params);
var env = BuildEnvFromParams.BUILD_ENV.fetchFrom(params);
LinuxPackagingPipeline.build()
LinuxPackagingPipeline.build(Optional.empty())
.excludeDirFromCopying(output.getParent())
.create().execute(BuildEnv.withAppImageDir(env, output), app);
});
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,10 @@
*/
package jdk.jpackage.internal;

import static jdk.jpackage.internal.util.PathUtils.resolveNullablePath;
import static jdk.jpackage.internal.util.PathUtils.mapNullablePath;

import java.nio.file.Path;
import java.util.function.UnaryOperator;
import jdk.jpackage.internal.model.ApplicationLayout;
import jdk.jpackage.internal.util.CompositeProxy;

Expand All @@ -40,7 +41,25 @@ static LinuxApplicationLayout create(ApplicationLayout layout, Path libAppLaunch

@Override
default LinuxApplicationLayout resolveAt(Path root) {
return create(ApplicationLayout.super.resolveAt(root),
resolveNullablePath(root, libAppLauncher()));
return (LinuxApplicationLayout)ApplicationLayout.super.resolveAt(root);
}

@Override
default LinuxApplicationLayout unresolve() {
return (LinuxApplicationLayout)ApplicationLayout.super.unresolve();
}

@Override
default LinuxApplicationLayout resetRootDirectory() {
if (isResolved()) {
return create(ApplicationLayout.super.resetRootDirectory(), libAppLauncher());
} else {
return this;
}
}

@Override
default LinuxApplicationLayout map(UnaryOperator<Path> mapper) {
return create(ApplicationLayout.super.map(mapper), mapNullablePath(mapper, libAppLauncher()));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@

import java.nio.file.Path;

// Must be publc to allow access from AppImageLayout.toPathGroup()
// Must be public to allow access from AppImageLayout.toPathGroup()
public interface LinuxApplicationLayoutMixin {

/**
Expand Down
Loading