Skip to content

Commit 6f43811

Browse files
KristofferCKristofferC
authored andcommitted
slot into the package loading system for portable scripts
1 parent bf6b148 commit 6f43811

12 files changed

+60
-19
lines changed

base/client.jl

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -346,7 +346,17 @@ function exec_options(opts)
346346
if PROGRAM_FILE == "-"
347347
include_string(Main, read(stdin, String), "stdin")
348348
else
349-
include(Main, PROGRAM_FILE)
349+
abs_script_path = abspath(PROGRAM_FILE)
350+
if has_inline_project(abs_script_path)
351+
set_portable_script_state(abs_script_path)
352+
try
353+
include(Main, PROGRAM_FILE)
354+
finally
355+
global portable_script_state_global = nothing
356+
end
357+
else
358+
include(Main, PROGRAM_FILE)
359+
end
350360
end
351361
catch
352362
invokelatest(display_error, scrub_repl_backtrace(current_exceptions()))

base/loading.jl

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -346,6 +346,24 @@ function has_inline_project(path::String)::Bool
346346
end
347347

348348

349+
struct PortableScriptState
350+
path::String
351+
pkg::PkgId
352+
end
353+
354+
portable_script_state_global::Union{PortableScriptState, Nothing} = nothing
355+
356+
function set_portable_script_state(abs_path::Union{Nothing, String})
357+
pkg = project_file_name_uuid(abs_path, splitext(basename(abs_path))[1])
358+
359+
# Verify the project and manifest delimiters:
360+
parsed_toml(abs_path)
361+
parsed_toml(abs_path; manifest=true)
362+
363+
global portable_script_state_global = PortableScriptState(abs_path, pkg)
364+
end
365+
366+
349367
struct LoadingCache
350368
load_path::Vector{String}
351369
dummy_uuid::Dict{String, UUID}
@@ -440,7 +458,12 @@ end
440458
Same as [`Base.identify_package`](@ref) except that the path to the environment where the package is identified
441459
is also returned, except when the identity is not identified.
442460
"""
443-
identify_package_env(where::Module, name::String) = identify_package_env(PkgId(where), name)
461+
function identify_package_env(where::Module, name::String)
462+
if where === Main && portable_script_state_global !== nothing
463+
return identify_package_env(portable_script_state_global.pkg, name)
464+
end
465+
return identify_package_env(PkgId(where), name)
466+
end
444467
function identify_package_env(where::Union{PkgId, Nothing}, name::String)
445468
# Special cases
446469
if where !== nothing

test/loading.jl

Lines changed: 14 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1873,7 +1873,7 @@ module M58272_to end
18731873

18741874
@testset "Portable scripts" begin
18751875
# Test with line-by-line comment syntax and path dependencies
1876-
portable_script = joinpath(@__DIR__, "project", "portable_script.jl")
1876+
portable_script = joinpath(@__DIR__, "project", "portable", "portable_script.jl")
18771877
output = read(`$(Base.julia_cmd()) --startup-file=no $portable_script`, String)
18781878

18791879
@test occursin("Active project: $portable_script", output)
@@ -1886,9 +1886,9 @@ module M58272_to end
18861886
@test occursin("Pass", output)
18871887

18881888
# Test with custom manifest= entry in project section
1889-
portable_script_cm = joinpath(@__DIR__, "project", "portable_script_custom_manifest.jl")
1889+
portable_script_cm = joinpath(@__DIR__, "project", "portable", "portable_script_custom_manifest.jl")
18901890
output_cm = read(`$(Base.julia_cmd()) --startup-file=no $portable_script_cm`, String)
1891-
expected_cm = joinpath(@__DIR__, "project", "portable_script_custom.toml")
1891+
expected_cm = joinpath(@__DIR__, "project", "portable", "portable_script_custom.toml")
18921892

18931893
@test occursin("Active project: $portable_script_cm", output_cm)
18941894
@test occursin("Active manifest: $expected_cm", output_cm)
@@ -1904,7 +1904,7 @@ module M58272_to end
19041904
@test occursin("✓ Random (stdlib) loaded successfully", output_script)
19051905

19061906
# Test that regular Julia files (without inline sections) work fine as projects
1907-
regular_script = joinpath(@__DIR__, "project", "regular_script.jl")
1907+
regular_script = joinpath(@__DIR__, "project", "portable", "regular_script.jl")
19081908

19091909
# Running the script with --project= should set it as active project
19101910
output = read(`$(Base.julia_cmd()) --startup-file=no --project=$regular_script $regular_script`, String)
@@ -1918,29 +1918,35 @@ module M58272_to end
19181918
@test occursin("Hello from regular script", output)
19191919
@test occursin("x = 42", output)
19201920

1921+
portable_script_missing = joinpath(@__DIR__, "project", "portable", "portable_script_missing_dep.jl")
1922+
err_output = IOBuffer()
1923+
result = run(pipeline(ignorestatus(`$(Base.julia_cmd()) --startup-file=no $portable_script_missing`), stderr=err_output))
1924+
@test !success(result)
1925+
@test occursin("Package Rot13 not found in current path", String(take!(err_output)))
1926+
19211927
# Test 1: Project section not first (has code before it)
1922-
invalid_project_not_first = joinpath(@__DIR__, "project", "invalid_project_not_first.jl")
1928+
invalid_project_not_first = joinpath(@__DIR__, "project", "portable", "invalid_project_not_first.jl")
19231929
err_output = IOBuffer()
19241930
result = run(pipeline(ignorestatus(`$(Base.julia_cmd()) --startup-file=no $invalid_project_not_first`), stderr=err_output))
19251931
@test !success(result)
19261932
@test occursin("#!project section must come first", String(take!(err_output)))
19271933

19281934
# Test 2: Manifest section not last (has code after it)
1929-
invalid_manifest_not_last = joinpath(@__DIR__, "project", "invalid_manifest_not_last.jl")
1935+
invalid_manifest_not_last = joinpath(@__DIR__, "project", "portable", "invalid_manifest_not_last.jl")
19301936
err_output = IOBuffer()
19311937
result = run(pipeline(ignorestatus(`$(Base.julia_cmd()) --startup-file=no $invalid_manifest_not_last`), stderr=err_output))
19321938
@test !success(result)
19331939
@test occursin("#!manifest section must come last", String(take!(err_output)))
19341940

19351941
# Test 3: Project not first, but manifest present
1936-
invalid_both = joinpath(@__DIR__, "project", "invalid_both.jl")
1942+
invalid_both = joinpath(@__DIR__, "project", "portable", "invalid_both.jl")
19371943
err_output = IOBuffer()
19381944
result = run(pipeline(ignorestatus(`$(Base.julia_cmd()) --startup-file=no --project=$invalid_both -e "using Test"`), stderr=err_output))
19391945
@test !success(result)
19401946
@test occursin("#!project section must come first", String(take!(err_output)))
19411947

19421948
# Test 4: Manifest with code in between sections
1943-
invalid_code_between = joinpath(@__DIR__, "project", "invalid_code_between.jl")
1949+
invalid_code_between = joinpath(@__DIR__, "project", "portable", "invalid_code_between.jl")
19441950
err_output = IOBuffer()
19451951
result = run(pipeline(ignorestatus(`$(Base.julia_cmd()) --startup-file=no --project=$invalid_code_between -e "using Test"`), stderr=err_output))
19461952
@test !success(result)

test/project/invalid_both.jl renamed to test/project/portable/invalid_both.jl

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,3 @@
1-
using Test
2-
31
function foo()
42
return 42
53
end

test/project/invalid_code_between.jl renamed to test/project/portable/invalid_code_between.jl

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,6 @@
11
#!project begin
22
#!project end
33

4-
using Test
5-
64
# Some actual Julia code
75
function bar()
86
println("hello")

test/project/invalid_manifest_not_last.jl renamed to test/project/portable/invalid_manifest_not_last.jl

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,6 @@
33
# Test = "8dfed614-e22c-5e08-85e1-65c5234f0b40"
44
#!project end
55

6-
using Test
7-
86
#!manifest begin
97
# julia_version = "1.11.0"
108
#!manifest end

test/project/invalid_project_not_first.jl renamed to test/project/portable/invalid_project_not_first.jl

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
# Some code before project section
22

3-
using Test
43
x = 1
54

65
#!project begin

test/project/portable_script.jl renamed to test/project/portable/portable_script.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@ end
8585
# version = "1.11.0"
8686
#
8787
# [[deps.Rot13]]
88-
# path = "Rot13"
88+
# path = "../Rot13"
8989
# uuid = "43ef800a-eac4-47f4-949b-25107b932e8f"
9090
# version = "0.1.0"
9191
#!manifest end

test/project/portable_script_custom.toml renamed to test/project/portable/portable_script_custom.toml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
julia_version = "1.13.0"
22
manifest_format = "2.0"
3-
project_hash = "custom_manifest_test"
43

54
[[deps.Random]]
65
uuid = "9a3f8284-a2c9-5f02-9a11-845980a1fd5c"

0 commit comments

Comments
 (0)