To be able to edit code and run cells, you need to run the notebook yourself. Where would you like to run the notebook?

In the cloud (experimental)

Binder is a free, open source service that runs scientific notebooks in the cloud! It will take a while, usually 2-7 minutes to get a session.

On your computer

(Recommended if you want to store your changes.)

  1. Copy the notebook URL:
  2. Run Pluto

    (Also see: How to install Julia and Pluto)

  3. Paste URL in the Open box

Frontmatter

If you are publishing this notebook on the web, you can set the parameters below to provide HTML metadata. This is useful for search engines and social media.

Author 1

To use these packages...

(Edit me!)

👀 Reading hidden code
206 μs
👀 Reading hidden code
222 ms

... you can use this Pkg cell!

(Copy me!)

👀 Reading hidden code
206 μs
Error message

Another cell defining PkgTools contains errors.

👀 Reading hidden code
Markdown.MD(Markdown.Code("julia", code))
---




Appendix

👀 Reading hidden code
105 μs
👀 Reading hidden code
package_names = setdiff(
split(replace(packages_raw, r"\W" => " "), keepempty=false),
["using", "import"]
)
64.7 ms
Error message

UndefVarError: is_stdlib not defined

code = """
begin
import Pkg
Pkg.activate(mktempdir())
Pkg.add([
$(join([
let
v = recommended_range(p)
vstring = v === nothing ? "" : ", version=\"$(v)\""

" Pkg.PackageSpec(name=\"$(p)\"$(vstring)),"
end
for p in filter(!PkgTools.is_stdlib, package_names)], "\n"))
])
using $(join(package_names, ", "))
end
""";
👀 Reading hidden code
---
Error message

UndefVarError: is_stdlib not defined

Try asking on Julia Discourse!
PkgTools.is_stdlib.(package_names)
👀 Reading hidden code
---
Error message

UndefVarError: is_stdlib not defined

Stack trace

Here is what happened, the most recent locations are first:

  1. recommended_range(package_name::SubString{String})
    function recommended_range(package_name::AbstractString)	if PkgTools.is_stdlib(package_name)		nothing	else
  2. Show more...
recommended_range.(package_names)
👀 Reading hidden code
---
Error message

UndefVarError: package_versions not defined

PkgTools.package_versions("Plots")
👀 Reading hidden code
---
v"1.2.3"
v = v"1.2.3"
👀 Reading hidden code
1.5 ms
false
v.major == 0
👀 Reading hidden code
15.6 μs
"0.0.123"
recommended_range([v"0.0.123"])
👀 Reading hidden code
31.3 μs
recommended_range (generic function with 1 method)
function recommended_range(v::VersionNumber)
if v.major == 0
if v.minor == 0
"0.0.$(v.patch)"
else
"0.$(v.minor)"
end
else
"$(v.major)"
end
end
👀 Reading hidden code
1.1 ms
recommended_range (generic function with 2 methods)
function recommended_range(versions::Vector{VersionNumber})
if isempty(versions)
nothing
else
v = maximum(versions)
recommended_range(v)
end
end
👀 Reading hidden code
549 μs
recommended_range (generic function with 3 methods)
function recommended_range(package_name::AbstractString)
if PkgTools.is_stdlib(package_name)
nothing
else
recommended_range(PkgTools.package_versions(package_name))
end
end
👀 Reading hidden code
502 μs
begin
import Pkg
Pkg.activate(mktempdir())
Pkg.add(["PlutoUI"])
using PlutoUI
end
👀 Reading hidden code
❔
  Activating new project at `/tmp/jl_pPWl0t`
    Updating registry at `~/.julia/registries/General.toml`
   Resolving package versions...
    Updating `/tmp/jl_pPWl0t/Project.toml`
  [7f904dfe] + PlutoUI v0.7.64
    Updating `/tmp/jl_pPWl0t/Manifest.toml`
  [6e696c72] + AbstractPlutoDingetjes v1.3.2
  [3da002f7] + ColorTypes v0.12.1
  [53c48c17] + FixedPointNumbers v0.8.5
  [47d2ed2b] + Hyperscript v0.0.5
  [ac1192a8] + HypertextLiteral v0.9.5
  [b5f81e59] + IOCapture v0.2.5
  [682c06a0] + JSON v0.21.4
  [6c6e2e6c] + MIMEs v1.1.0
  [69de0a69] + Parsers v2.8.3
  [7f904dfe] + PlutoUI v0.7.64
  [aea7be01] + PrecompileTools v1.2.1
  [21216c6a] + Preferences v1.4.3
  [189a3867] + Reexport v1.2.2
  [410a4b4d] + Tricks v0.1.10
  [5c2747f8] + URIs v1.5.2
  [0dad84c5] + ArgTools
  [56f22d72] + Artifacts
  [2a0f44e3] + Base64
  [ade2ca70] + Dates
  [f43a241f] + Downloads
  [7b1f6079] + FileWatching
  [b77e0a4c] + InteractiveUtils
  [b27032c2] + LibCURL
  [76f85450] + LibGit2
  [8f399da3] + Libdl
  [37e2e46d] + LinearAlgebra
  [56ddb016] + Logging
  [d6f4376e] + Markdown
  [a63ad114] + Mmap
  [ca575930] + NetworkOptions
  [44cfe95a] + Pkg
  [de0858da] + Printf
  [3fa0cd96] + REPL
  [9a3f8284] + Random
  [ea8e919c] + SHA
  [9e88b42a] + Serialization
  [6462fe0b] + Sockets
  [2f01184e] + SparseArrays
  [10745b16] + Statistics
  [fa267f1f] + TOML
  [a4e569a6] + Tar
  [8dfed614] + Test
  [cf7118a7] + UUIDs
  [4ec0a83e] + Unicode
  [e66e0078] + CompilerSupportLibraries_jll
  [deac9b47] + LibCURL_jll
  [29816b5a] + LibSSH2_jll
  [c8ffd9c3] + MbedTLS_jll
  [14a3606d] + MozillaCACerts_jll
  [4536629a] + OpenBLAS_jll
  [83775a58] + Zlib_jll
  [8e850b90] + libblastrampoline_jll
  [8e850ede] + nghttp2_jll
  [3f19e933] + p7zip_jll
2.0 s
👀 Reading hidden code
216 μs
Error message

UndefVarError: collect_registries not defined

Stack trace

Here is what happened, the most recent locations are first:

  1. getproperty(x::Module, f::Symbol)
    from Base.jl:35
  2. else	registry_specs = Pkg.Types.collect_registries()	[s.path for s in registry_specs]
  3. Show more...
module PkgTools

export package_versions, package_completions

import Pkg
import Pkg.Types: VersionRange

function getfirst(f::Function, xs)
for x ∈ xs
if f(x)
return x
end
end
error("Not found")
end

create_empty_ctx() = Pkg.Types.Context(env=Pkg.Types.EnvCache(joinpath(mktempdir(),"Project.toml")))

# TODO: technically this is not constant
const registry_paths = @static if isdefined(Pkg.Types, :registries)
Pkg.Types.registries()
else
registry_specs = Pkg.Types.collect_registries()
[s.path for s in registry_specs]
end

const registries = map(registry_paths) do r
r => Pkg.Types.read_registry(joinpath(r, "Registry.toml"))
end

const stdlibs = readdir(Pkg.Types.stdlib_dir())::Vector{String}

is_stdlib(package_name::AbstractString) = package_name ∈ stdlibs
is_stdlib(pkg::Pkg.Types.PackageEntry) = pkg.version === nothing && (pkg.name ∈ stdlibs)

# TODO: should this be the notebook context? it only matters for which registry is used
const global_ctx = Pkg.Types.Context()

###
# Package names
###

function registered_package_completions(partial_name::AbstractString)
# compat
@static if hasmethod(Pkg.REPLMode.complete_remote_package, (String,))
Pkg.REPLMode.complete_remote_package(partial_name)
else
Pkg.REPLMode.complete_remote_package(partial_name, 1, length(partial_name))[1]
end
end

function package_completions(partial_name::AbstractString)::Vector{String}
String[
filter(s -> startswith(s, partial_name), stdlibs);
registered_package_completions(partial_name)
]
end


###
# Package versions
###

function registries_path(registries::Vector, package_name::AbstractString)::Union{Nothing,String}
for (rpath, r) in registries
packages = values(r["packages"])
ds = Iterators.filter(d -> d["name"] == package_name, packages)
if !isempty(ds)
return joinpath(rpath, first(ds)["path"])
end
end
end

function package_versions_from_path(registry_entry_fullpath::AbstractString; ctx=global_ctx)::Vector{VersionNumber}
# compat
(@static if hasmethod(Pkg.Operations.load_versions, (String,))
Pkg.Operations.load_versions(registry_entry_fullpath)
else
Pkg.Operations.load_versions(ctx, registry_entry_fullpath)
end) |> keys |> collect |> sort!
end

function package_versions(package_name::AbstractString)::Vector
if package_name ∈ stdlibs
["stdlib"]
else
p = registries_path(registries, package_name)
if p === nothing
VersionNumber[]
else
package_versions_from_path(p)
end
end
end

package_exists(package_name::AbstractString) =
package_name ∈ stdlibs ||
registries_path(registries, package_name) !== nothing

get_manifest_entry(ctx::Pkg.Types.Context, package_name::AbstractString) =
getfirst(e -> e.name == package_name, values(ctx.env.manifest))

function get_manifest_version(ctx, package_name)
if package_name ∈ stdlibs
"stdlib"
else
entry = get_manifest_entry(ctx, package_name)
entry.version
end
end

end
👀 Reading hidden code
---