Skip to content

Commit e9b0fa1

Browse files
Add preference for version named manifest files (#43845)
Co-authored-by: Dilum Aluthge <dilum@aluthge.com>
1 parent ad2d770 commit e9b0fa1

File tree

6 files changed

+45
-6
lines changed

6 files changed

+45
-6
lines changed

NEWS.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,11 @@ New language features
1616
particularly useful for holding styling information, and is used extensively
1717
in the new `StyledStrings` standard library. There is also a new `AnnotatedChar`
1818
type, that is the equivalent new `AbstractChar` type.
19+
* `Manifest.toml` files can now be renamed in the format `Manifest-v{major}.{minor}.toml`
20+
to be preferentially picked up by the given julia version. i.e. in the same folder,
21+
a `Manifest-v1.11.toml` would be used by v1.11 and `Manifest.toml` by every other julia
22+
version. This makes managing environments for multiple julia versions at the same time
23+
easier ([#43845]).
1924

2025
Language changes
2126
----------------

base/loading.jl

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -566,7 +566,12 @@ end
566566
## generic project & manifest API ##
567567

568568
const project_names = ("JuliaProject.toml", "Project.toml")
569-
const manifest_names = ("JuliaManifest.toml", "Manifest.toml")
569+
const manifest_names = (
570+
"JuliaManifest-v$(VERSION.major).$(VERSION.minor).toml",
571+
"Manifest-v$(VERSION.major).$(VERSION.minor).toml",
572+
"JuliaManifest.toml",
573+
"Manifest.toml",
574+
)
570575
const preferences_names = ("JuliaLocalPreferences.toml", "LocalPreferences.toml")
571576

572577
function locate_project_file(env::String)

doc/src/manual/code-loading.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ Code inclusion is quite straightforward and simple: it evaluates the given sourc
1414

1515
A *package* is a source tree with a standard layout providing functionality that can be reused by other Julia projects. A package is loaded by `import X` or `using X` statements. These statements also make the module named `X`—which results from loading the package code—available within the module where the import statement occurs. The meaning of `X` in `import X` is context-dependent: which `X` package is loaded depends on what code the statement occurs in. Thus, handling of `import X` happens in two stages: first, it determines **what** package is defined to be `X` in this context; second, it determines **where** that particular `X` package is found.
1616

17-
These questions are answered by searching through the project environments listed in [`LOAD_PATH`](@ref) for project files (`Project.toml` or `JuliaProject.toml`), manifest files (`Manifest.toml` or `JuliaManifest.toml`), or folders of source files.
17+
These questions are answered by searching through the project environments listed in [`LOAD_PATH`](@ref) for project files (`Project.toml` or `JuliaProject.toml`), manifest files (`Manifest.toml` or `JuliaManifest.toml`, or the same names suffixed by `-v{major}.{minor}.toml` for specific versions), or folders of source files.
1818

1919

2020
## Federation of packages
@@ -63,7 +63,7 @@ Each kind of environment defines these three maps differently, as detailed in th
6363

6464
### Project environments
6565

66-
A project environment is determined by a directory containing a project file called `Project.toml`, and optionally a manifest file called `Manifest.toml`. These files may also be called `JuliaProject.toml` and `JuliaManifest.toml`, in which case `Project.toml` and `Manifest.toml` are ignored. This allows for coexistence with other tools that might consider files called `Project.toml` and `Manifest.toml` significant. For pure Julia projects, however, the names `Project.toml` and `Manifest.toml` are preferred.
66+
A project environment is determined by a directory containing a project file called `Project.toml`, and optionally a manifest file called `Manifest.toml`. These files may also be called `JuliaProject.toml` and `JuliaManifest.toml`, in which case `Project.toml` and `Manifest.toml` are ignored. This allows for coexistence with other tools that might consider files called `Project.toml` and `Manifest.toml` significant. For pure Julia projects, however, the names `Project.toml` and `Manifest.toml` are preferred. However, from Julia v1.11 onwards, `(Julia)Manifest-v{major}.{minor}.toml` is recognized as a format to make a given julia version use a specific manifest file i.e. in the same folder, a `Manifest-v1.11.toml` would be used by v1.11 and `Manifest.toml` by any other julia version.
6767

6868
The roots, graph and paths maps of a project environment are defined as follows:
6969

stdlib/Artifacts/src/Artifacts.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ function parse_toml(path::String)
1818
Base.parsed_toml(path)
1919
end
2020

21-
# keep in sync with Base.project_names and Base.manifest_names
21+
# keep in sync with Base.project_names
2222
const artifact_names = ("JuliaArtifacts.toml", "Artifacts.toml")
2323

2424
const ARTIFACTS_DIR_OVERRIDE = Ref{Union{String,Nothing}}(nothing)

stdlib/Artifacts/test/runtests.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -258,6 +258,6 @@ end
258258
@testset "`Artifacts.artifact_names` and friends" begin
259259
n = length(Artifacts.artifact_names)
260260
@test length(Base.project_names) == n
261-
@test length(Base.manifest_names) == n
261+
@test length(Base.manifest_names) == 2n # there are two manifest names per project name
262262
@test length(Base.preferences_names) == n
263263
end

test/loading.jl

Lines changed: 30 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -795,8 +795,10 @@ end
795795
@testset "`Base.project_names` and friends" begin
796796
# Some functions in Pkg assumes that these tuples have the same length
797797
n = length(Base.project_names)
798-
@test length(Base.manifest_names) == n
799798
@test length(Base.preferences_names) == n
799+
800+
# there are two manifest names per project name
801+
@test length(Base.manifest_names) == 2n
800802
end
801803

802804
@testset "Manifest formats" begin
@@ -825,6 +827,33 @@ end
825827
end
826828
end
827829

830+
@testset "Manifest name preferential loading" begin
831+
mktempdir() do tmp
832+
proj = joinpath(tmp, "Project.toml")
833+
touch(proj)
834+
for man_name in (
835+
"Manifest.toml",
836+
"JuliaManifest.toml",
837+
"Manifest-v$(VERSION.major).$(VERSION.minor).toml",
838+
"JuliaManifest-v$(VERSION.major).$(VERSION.minor).toml"
839+
)
840+
touch(joinpath(tmp, man_name))
841+
man = basename(Base.project_file_manifest_path(proj))
842+
@test man == man_name
843+
end
844+
end
845+
mktempdir() do tmp
846+
# check that another version isn't preferred
847+
proj = joinpath(tmp, "Project.toml")
848+
touch(proj)
849+
touch(joinpath(tmp, "Manifest-v1.5.toml"))
850+
@test Base.project_file_manifest_path(proj) == nothing
851+
touch(joinpath(tmp, "Manifest.toml"))
852+
man = basename(Base.project_file_manifest_path(proj))
853+
@test man == "Manifest.toml"
854+
end
855+
end
856+
828857
@testset "error message loading pkg bad module name" begin
829858
mktempdir() do tmp
830859
old_loadpath = copy(LOAD_PATH)

0 commit comments

Comments
 (0)