diff --git a/pkl-core/src/main/java/org/pkl/core/packages/Dependency.java b/pkl-core/src/main/java/org/pkl/core/packages/Dependency.java index 5f75eed5..8cbe7e9f 100644 --- a/pkl-core/src/main/java/org/pkl/core/packages/Dependency.java +++ b/pkl-core/src/main/java/org/pkl/core/packages/Dependency.java @@ -1,5 +1,5 @@ /* - * Copyright © 2024 Apple Inc. and the Pkl project authors. All rights reserved. + * Copyright © 2024-2026 Apple Inc. and the Pkl project authors. All rights reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -16,8 +16,10 @@ package org.pkl.core.packages; import java.net.URI; +import java.net.URISyntaxException; import java.nio.file.Path; import java.util.Objects; +import org.pkl.core.PklBugException; import org.pkl.core.Version; import org.pkl.core.util.IoUtils; import org.pkl.core.util.Nullable; @@ -53,7 +55,15 @@ public abstract class Dependency { public URI resolveAssetUri(URI projectBaseUri, PackageAssetUri packageAssetUri) { // drop 1 to remove leading `/` var assetPath = packageAssetUri.getAssetPath().substring(1); - return projectBaseUri.resolve(IoUtils.toNormalizedPathString(path.resolve(assetPath))); + var resolvedPath = path.resolve(assetPath); + var normalized = IoUtils.toNormalizedPathString(resolvedPath); + try { + var relativeUri = new URI(null, null, normalized, null); + return projectBaseUri.resolve(relativeUri); + } catch (URISyntaxException e) { + // impossible; we started from valid URIs to begin with. + throw PklBugException.unreachableCode(); + } } @Override diff --git a/pkl-core/src/main/java/org/pkl/core/packages/PackageAssetUri.java b/pkl-core/src/main/java/org/pkl/core/packages/PackageAssetUri.java index f3f0648a..3df58cbb 100644 --- a/pkl-core/src/main/java/org/pkl/core/packages/PackageAssetUri.java +++ b/pkl-core/src/main/java/org/pkl/core/packages/PackageAssetUri.java @@ -1,5 +1,5 @@ /* - * Copyright © 2024 Apple Inc. and the Pkl project authors. All rights reserved. + * Copyright © 2024-2026 Apple Inc. and the Pkl project authors. All rights reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -18,6 +18,7 @@ package org.pkl.core.packages; import java.net.URI; import java.net.URISyntaxException; import java.nio.file.Path; +import org.pkl.core.PklBugException; import org.pkl.core.Version; import org.pkl.core.util.ErrorMessages; import org.pkl.core.util.IoUtils; @@ -40,7 +41,13 @@ public final class PackageAssetUri { } public PackageAssetUri(PackageUri packageUri, String assetPath) { - this.uri = packageUri.getUri().resolve("#" + assetPath); + var base = packageUri.getUri(); + try { + this.uri = new URI(base.getScheme(), base.getSchemeSpecificPart(), assetPath); + } catch (URISyntaxException e) { + // impossible condition, we have a valid URI to start with. + throw PklBugException.unreachableCode(); + } this.packageUri = packageUri; this.assetPath = assetPath; } diff --git a/pkl-core/src/test/files/LanguageSnippetTests/input/projects/packageWithSpaces/PklProject b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/packageWithSpaces/PklProject new file mode 100644 index 00000000..4a5e49bb --- /dev/null +++ b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/packageWithSpaces/PklProject @@ -0,0 +1,8 @@ +amends "pkl:Project" + +package { + name = "packageWithSpaces" + baseUri = "package://localhost:0/packageWithSpaces" + version = "1.0.0" + packageZipUrl = "https://localhost:0/packageWithSpaces/packageWithSpaces-\(version).zip" +} diff --git a/pkl-core/src/test/files/LanguageSnippetTests/input/projects/packageWithSpaces/module with spaces.pkl b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/packageWithSpaces/module with spaces.pkl new file mode 100644 index 00000000..c4e5bcc8 --- /dev/null +++ b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/packageWithSpaces/module with spaces.pkl @@ -0,0 +1 @@ +foo = 1 diff --git a/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/PklProject b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/PklProject new file mode 100644 index 00000000..4d48cfcb --- /dev/null +++ b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/PklProject @@ -0,0 +1,8 @@ +amends "pkl:Project" + +dependencies { + ["birds"] { + uri = "package://localhost:0/birds@0.7.0" + } + ["packageWithSpaces"] = import("../packageWithSpaces/PklProject") +} diff --git a/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/PklProject.deps.json b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/PklProject.deps.json new file mode 100644 index 00000000..749d8e97 --- /dev/null +++ b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/PklProject.deps.json @@ -0,0 +1,17 @@ +{ + "schemaVersion": 1, + "resolvedDependencies": { + "package://localhost:0/birds@0": { + "type": "remote", + "uri": "projectpackage://localhost:0/birds@0.7.0", + "checksums": { + "sha256": "$skipChecksumVerification" + } + }, + "package://localhost:0/packageWithSpaces@1": { + "type": "local", + "uri": "projectpackage://localhost:0/packageWithSpaces@1.0.0", + "path": "../packageWithSpaces/" + } + } +} diff --git a/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/globWildcards.pkl b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/globWildcards.pkl new file mode 100644 index 00000000..c42718bf --- /dev/null +++ b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/globWildcards.pkl @@ -0,0 +1,3 @@ +import* "@birds/catalog/{Ostrich,Swallow}.pkl" as myCatalog + +res = myCatalog.keys diff --git a/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/spacesInImport.pkl b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/spacesInImport.pkl new file mode 100644 index 00000000..035e9313 --- /dev/null +++ b/pkl-core/src/test/files/LanguageSnippetTests/input/projects/project7/spacesInImport.pkl @@ -0,0 +1,3 @@ +import "@packageWithSpaces/module with spaces.pkl" as mod + +res = mod diff --git a/pkl-core/src/test/files/LanguageSnippetTests/output/projects/packageWithSpaces/module with spaces.pcf b/pkl-core/src/test/files/LanguageSnippetTests/output/projects/packageWithSpaces/module with spaces.pcf new file mode 100644 index 00000000..c4e5bcc8 --- /dev/null +++ b/pkl-core/src/test/files/LanguageSnippetTests/output/projects/packageWithSpaces/module with spaces.pcf @@ -0,0 +1 @@ +foo = 1 diff --git a/pkl-core/src/test/files/LanguageSnippetTests/output/projects/project7/globWildcards.pcf b/pkl-core/src/test/files/LanguageSnippetTests/output/projects/project7/globWildcards.pcf new file mode 100644 index 00000000..2f62a757 --- /dev/null +++ b/pkl-core/src/test/files/LanguageSnippetTests/output/projects/project7/globWildcards.pcf @@ -0,0 +1 @@ +res = Set("@birds/catalog/Ostrich.pkl", "@birds/catalog/Swallow.pkl") diff --git a/pkl-core/src/test/files/LanguageSnippetTests/output/projects/project7/spacesInImport.pcf b/pkl-core/src/test/files/LanguageSnippetTests/output/projects/project7/spacesInImport.pcf new file mode 100644 index 00000000..261d681b --- /dev/null +++ b/pkl-core/src/test/files/LanguageSnippetTests/output/projects/project7/spacesInImport.pcf @@ -0,0 +1,3 @@ +res { + foo = 1 +}