# Proper way to create sysimage with all dependencies of a given package

**URL:** <https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460>\
**Category:** General Usage\
**Tags:** package-compiler, sysimage\
**Created:** [December 9, 2022, 8:07am UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460 "2022-12-09T08:07:58Z")\
**Posts on this page:** 10\
**Page:** 1

<div class="post-metadata">

**Author:** ![sloede](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sloede/32/44787_2.png) [@sloede](https://discourse.julialang.org/u/sloede)\
**Post date:** [December 9, 2022, 8:07am UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460/1 "2022-12-09T08:07:58Z")

</div>

What’s the proper way to create a custom sysimage for the following situation:

I am developing a package with at least a moderately large set of dependencies ([Trixi.jl](https://github.com/trixi-framework/Trixi.jl)) and I would like to speed up startup latency by compiling all dependencies into a sysimage with [PackageCompiler.jl](https://github.com/JuliaLang/PackageCompiler.jl). How do I properly invoke PC.jl such that all dependencies are included but not my package itself (since I am actively developing it)?

Right now, I am doing something like the following, where I copy the `Project.toml` from my package to another folder, remove the everything but the `[deps]` and `[compat]` sections, instantiate it, then install my package in the same environment, and finallly run PC.jl with a script that exercises some functions of my package that in turn make use of the dependencies.

This seems like overly convoluted, thus I am sure that there must be an easier way to do it, right? During development, I usually run `julia --project` in my cloned package directory, and ideally I could just do that with a “special” PC.jl invocation to create a suitable sysimage.

---

<div class="post-metadata">

**Author:** ![skleinbo](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/skleinbo/32/36080_2.png) [@skleinbo](https://discourse.julialang.org/u/skleinbo)\
**Post date:** [December 9, 2022, 8:33am UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460/2 "2022-12-09T08:33:27Z")

</div>

You can specify the packages for which the sysimage is built as the first argument to `create_sysimage`

> ```julia
> create_sysimage(packages::Vector{String}; kwargs...)
> 
> ```
> 
> Create a system image that includes the package(s) in `packages` (given as a string or vector). If the `packages` argument is not passed, all packages in the project will be put into the sysimage.

> **[References · PackageCompiler](https://julialang.github.io/PackageCompiler.jl/stable/refs.html#PackageCompiler.create_sysimage)**
>
> Documentation for PackageCompiler.

---

<div class="post-metadata">

**Author:** ![sloede](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sloede/32/44787_2.png) [@sloede](https://discourse.julialang.org/u/sloede)\
**Post date:** [December 9, 2022, 8:44am UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460/3 "2022-12-09T08:44:07Z")

</div>

Thanks for the reply! Yes, I am aware of this argument, and this is what I currently use as well. However, I am wondering if there really is no other solution than to extract the package names manually from the `Project.toml`. I am looking for something (logically, not literally) like `create_sysimages(depsof(Trixi), ...)` where `depsof` will return all dependencies of a given package, or alternatively where I can include all packages in the current project _except_ a certain package.

---

<div class="post-metadata">

**Author:** ![skleinbo](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/skleinbo/32/36080_2.png) [@skleinbo](https://discourse.julialang.org/u/skleinbo)\
**Post date:** [December 9, 2022, 8:47am UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460/4 "2022-12-09T08:47:52Z")

</div>

You can use `Pkg.dependencies()` to get a dictionary of all packages in the environment, and massage that into a vector of names.

```julia
depsof(package::String) = filter(!=(package), map(p->p.name, values(Pkg.dependencies())))

```

---

<div class="post-metadata">

**Author:** ![sloede](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/sloede/32/44787_2.png) [@sloede](https://discourse.julialang.org/u/sloede)\
**Post date:** [January 7, 2023, 5:52am UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460/5 "2023-01-07T05:52:01Z")

</div>

Is there a way to really get only the direct dependencies of a given package? For example, sometimes I might have other, auxiliary packages in the same environment, such as OrdinaryDiffEq.jl.

---

<div class="post-metadata">

**Author:** ![kristoffer.carlsson](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/kristoffer.carlsson/32/22_2.png) [@kristoffer.carlsson](https://discourse.julialang.org/u/kristoffer.carlsson)\
**Post date:** [January 7, 2023, 7:47am UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460/6 "2023-01-07T07:47:13Z")

</div>

> [@sloede](#):
>
> Is there a way to really get only the direct dependencies of a given package?

You can do something like:

```julia
julia> uuid_dataframes = only(findall(x -> x.name == "DataFrames", Pkg.dependencies()))
UUID("a93c6f00-e57d-5684-b7b6-d8193f3e46c0")

julia> Pkg.dependencies()[uuid_dataframes].dependencies
Dict{String, Base.UUID} with 18 entries:
  "Statistics" => UUID("10745b16-79ce-11e8-11f9-7d13ad32a3b2")
  "SortingAlgorithms" => UUID("a2af1166-a08f-5f64-846c-94a0d3cef48c")
  "PooledArrays" => UUID("2dfb63ee-cc39-5dd5-95bd-886bf059d720")
  "TableTraits" => UUID("3783bdb8-4a98-5b6b-af9a-565f29a5fe9c")
  "REPL" => UUID("3fa0cd96-eef1-5676-8a61-b3b8758bbffb")
  "InvertedIndices" => UUID("41ab1584-1d38-5bbf-9106-f11c6c58b48f")
  "LinearAlgebra" => UUID("37e2e46d-f89d-539d-b4ee-838fcccc9c8e")
  "Missings" => UUID("e1d29d7a-bbdc-5cf2-9ac0-f12de2c33e28")
  "IteratorInterfaceExtensions" => UUID("82899510-4779-5014-852e-03e436cf321d")
  "Compat" => UUID("34da2185-b29b-5c13-b0c7-acf172513d20")
  "Tables" => UUID("bd369af6-aec1-5ad0-b16a-f7cc5008161c")
  "Unicode" => UUID("4ec0a83e-493e-50e2-b9ac-8f72acf5a8f5")
  "DataAPI" => UUID("9a962f9c-6df0-11e9-0e5d-c546b8b5ee8a")
  "Future" => UUID("9fa8497b-333b-5362-9e8d-4d0656e87820")
  "Printf" => UUID("de0858da-6303-5e67-8744-51eddeeeb8d7")
  "Markdown" => UUID("d6f4376e-aef5-505a-96c1-9c027394607a")
  "PrettyTables" => UUID("08abe8d2-0d0c-5749-adfa-8a2ac140af0d")
  "Reexport" => UUID("189a3867-3050-52da-a836-e630ba90ab69")

```

---

<div class="post-metadata">

**Author:** ![Ashlin\_Harris](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ashlin_harris/32/210166_2.png) [@Ashlin\_Harris](https://discourse.julialang.org/u/Ashlin_Harris)\
**Post date:** [February 21, 2023, 6:00pm UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460/7 "2023-02-21T18:00:28Z")

</div>

In a [related project](https://github.com/bcbi/SIEGE/blob/4353792c38a65fc9b1f7bbb08e6fd026498b9845/src/SIEGE.jl#L47-#L57), we’ve used the following to automatically extract and filter the dependencies from an existing environment:

```julia
	# Get all packages from the current project
	all_packages = String[]
	for (uuid, dep) in Pkg.dependencies()
		dep.is_direct_dep || continue
		dep.version === nothing && continue
		push!(all_packages,dep.name)
	end

	# Remove unneeded packages
	do_not_include = ["PackageCompiler","SIEGE"]
	package_list = filter(x -> x ∉ do_not_include, all_packages)

```

---

<div class="post-metadata">

**Author:** ![ellocco](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ellocco/32/31331_2.png) [@ellocco](https://discourse.julialang.org/u/ellocco)\
**Post date:** [February 22, 2023, 11:33am UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460/8 "2023-02-22T11:33:48Z")

</div>

What, if the `UUID` is not unique. This the case if my local clone of a project should be taken instead of the version that is public and has the same `UUID`?

---

<div class="post-metadata">

**Author:** ![Ashlin\_Harris](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ashlin_harris/32/210166_2.png) [@Ashlin\_Harris](https://discourse.julialang.org/u/Ashlin_Harris)\
**Post date:** [February 22, 2023, 2:18pm UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460/9 "2023-02-22T14:18:16Z")

</div>

This method would just use whichever version is in the current environment. I don’t think it’s possible to have both. For instance, when I try the following, adding the local version just replaces the public version, and vice versa.

```julia
pkg> activate --temp
pkg> add MyPackage # public version
pkg> dev /path/to/local/MyPackage

```

---

<div class="post-metadata">

**Author:** ![ellocco](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ellocco/32/31331_2.png) [@ellocco](https://discourse.julialang.org/u/ellocco)\
**Post date:** [February 22, 2023, 3:06pm UTC](https://discourse.julialang.org/t/proper-way-to-create-sysimage-with-all-dependencies-of-a-given-package/91460/10 "2023-02-22T15:06:37Z")

</div>

This is not sufficient ☹ See: [Missing Relocatability of Tulip - #9 by ellocco](https://discourse.julialang.org/t/missing-relocatability-of-tulip/94886/9)
