Skip to content

Commit

Permalink
Support merging of registries.
Browse files Browse the repository at this point in the history
  • Loading branch information
GunnarFarneback committed May 24, 2020
1 parent 48f2e12 commit b24771c
Show file tree
Hide file tree
Showing 4 changed files with 88 additions and 1 deletion.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -100,3 +100,4 @@ of the package's `Project.toml` file.

* [Working with a Private Registry and/or Private Repositories](docs/ssh_keys.md)
* [Registering a Package in a Subdirectory of a Repository](docs/subdir.md)
* [Merging Registries](docs/merge.md)
22 changes: 22 additions & 0 deletions docs/merge.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
If you for some reason have two registries that should only be one or
you want to copy some packages from one registry to another, you can
use the function `LocalRegistry.merge` (not exported).

LocalRegistry.merge(target_path, source_path)

Copy all packages in the registry at `source_path` into the
registry at `target_path`.

LocalRegistry.merge(target_path, source_path, include = ["A", "B"])

Copy only the packages `A` and `B`.

LocalRegistry.merge(target_path, source_path, exclude = ["A", "B"])

Copy all packages except `A` and `B`.

----

This gives an error if you try to copy a package that already exists
in the target repository. There is no built in support for commiting
or pushing the target registry.
4 changes: 3 additions & 1 deletion src/LocalRegistry.jl
Original file line number Diff line number Diff line change
Expand Up @@ -14,12 +14,14 @@ module LocalRegistry

using RegistryTools: RegistryTools, gitcmd, Compress,
check_and_update_registry_files, ReturnStatus, haserror,
find_registered_version
find_registered_version, parse_registry
using UUIDs: uuid4
using Pkg: Pkg, TOML

export create_registry, register

include("merge.jl")

# Note: The `uuid` keyword argument is intentionally omitted from the
# documentation string since it's not intended for users.
"""
Expand Down
62 changes: 62 additions & 0 deletions src/merge.jl
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
using RegistryTools: write_registry

function merge(target_path::AbstractString,
source_path::AbstractString;
include::Union{Nothing, Vector{<:AbstractString}} = nothing,
exclude::Union{Nothing, Vector{<:AbstractString}} = nothing)
if !isnothing(include) && !isnothing(exclude)
error("Packages can be either included or excluded, not both.")
end

target_registry = parse_registry(joinpath(target_path, "Registry.toml"))
source_registry = parse_registry(joinpath(source_path, "Registry.toml"))

target_packages = target_registry.packages
packages = source_registry.packages

if !isnothing(include)
packages = filter(p -> last(p)["name"] in include, packages)
if length(packages) != length(include)
missing_packages = setdiff(include, [p["name"] for p in values(packages)])
error("Included packages $(missing_packages) do not exist in the source repository")
end
end

if !isnothing(exclude)
missing_packages = setdiff(exclude, [p["name"] for p in values(packages)])
if !isempty(missing_packages)
error("Excluded packages $(missing_packages) do not exist in the source repository")
end
packages = filter(p -> last(p)["name"] exclude, packages)
end

colliding_names = intersect([p["name"] for p in values(target_packages)],
[p["name"] for p in values(packages)])
if !isempty(colliding_names)
error("The target registry already contains these packages: $(colliding_names).")
end

colliding_uuids = intersect(keys(target_packages), keys(packages))
if !isempty(colliding_uuids)
error("The target registry already contains these uuids: $(colliding_uuids).")
end

for (uuid, package) in packages
push!(target_packages, uuid => package)
package_dir = joinpath(target_path, package["path"])
if isdir(package_dir)
error("Package dir ", package["path"], " already exists in target registry.")
end
mkpath(package_dir)
for filename in ("Package.toml", "Versions.toml",
"Deps.toml", "Compat.toml")
from = joinpath(source_path, package["path"], filename)
to = joinpath(target_path, package["path"], filename)
if isfile(from)
cp(from, to)
end
end
end

write_registry(joinpath(target_path, "Registry.toml"), target_registry)
end

0 comments on commit b24771c

Please sign in to comment.