How to create a system image with Makie.jl

I created a system image containing Makie.jl using the following steps:

julia --project
]add PackageCompiler
add MakieGallery

exit()
julia --project
using MakieGallery

exit()
julia --project
using Makie
using PackageCompiler

PackageCompiler.create_sysimage(
    :Makie;
    sysimage_path="MakieSys.so",
    precompile_execution_file=joinpath(pkgdir(Makie), "test", "test_for_precompile.jl")
)

I launch julia with the command:

julia -J MakieSys.so --project

I execute:

include("src/KiteViewer.jl")

→ works fine

I execute:

main()

and get the following stack trace:

julia> main()
ERROR: MethodError: no method matching (Button{ArgType} where ArgType)(::Scene; label="RESET")
Closest candidates are:
  (::Type{var"#s199"} where var"#s199"<:AbstractPlot{Typ})(::SceneLike, ::Attributes, ::Any) where Typ at /home/ufechner/.julia/packages/AbstractPlotting/JCbJs/src/interfaces.jl:418 got unsupported keyword argument "label"
  (::Type{var"#s199"} where var"#s199"<:AbstractPlot{Typ})(::SceneLike, ::Attributes, ::Any, ::Any) where Typ at /home/ufechner/.julia/packages/AbstractPlotting/JCbJs/src/interfaces.jl:439 got unsupported keyword argument "label"
  (::Type{var"#s199"} where var"#s199"<:Combined)(::Any, ::Any, ::Any, ::Any, ::Any) at /home/ufechner/.julia/packages/AbstractPlotting/JCbJs/src/interfaces.jl:357 got unsupported keyword argument "label"
Stacktrace:
 [1] main(gl_wait::Bool)
   @ Main ~/repos/KiteViewer/src/KiteViewer.jl:153
 [2] main()
   @ Main ~/repos/KiteViewer/src/KiteViewer.jl:135
 [3] top-level scope
   @ REPL[2]:1

If I comment the buttons and the slider in the source code everything works fine.

Any idea?

I am using Julia 1.6 rc1 on Linux 64 bit and the following source code:

1 Like

The same code with the exact same package versions you compiled into your image works, if you do it without the sysimage? It’s weird that Button is missing but layoutscene earlier in your code and GridLayout are available. That means MakieLayout is exported somehow without Button, or something else as a side effect of the package compilation.

Yes, the same code works without the modified sysimage, but I had to add the lines:

using AbstractPlotting, AbstractPlotting.MakieLayout

when using the sysimage to get rid of messages that some layout related stuff is missing.

In other words: Yes, I think MakieLayout is somehow missing. How can I add it?

I identified the problem. Installing MakieGallery for creating a system image downgraded Makie which made my code fail. See: How to use a Button in GLMakie

No solution yet for the original question, though, because by default it requires MakieGallery.

So we need a replacement for this script:

ufechner@TUD277255:~$ cat /home/ufechner/.julia/packages/Makie/iTycG/test/test_for_precompile.jl
using MakieGallery, AbstractPlotting, GLMakie, Test

empty!(MakieGallery.plotting_backends)
push!(MakieGallery.plotting_backends, "Makie")
database = MakieGallery.load_database([
                    "tutorials.jl",
                    "attributes.jl",
                    "short_tests.jl"
                    ])

test_record_path = joinpath(@__DIR__, "test_recordings")
recordings = MakieGallery.record_examples(test_record_path)
@assert length(recordings) == length(database)
@info "Precompile script has completed execution."

I created an issue: The script test_for_precompile.jl is not compatible with the current version of Makie · Issue #845 · JuliaPlots/Makie.jl · GitHub

I created my own test_for_precompile.jl script, see KiteViewer/test_for_precompile.jl at main · ufechner7/KiteViewer · GitHub

I even created a script create_sys_image.sh , see: KiteViewer/create_sys_image.sh at main · ufechner7/KiteViewer · GitHub .

This works very well, startup time is reduced from 41s to 4s .

2 Likes

Thanks, I’m going to borrow this! You include Makie explicitly though; I thought the Makie package itself was basically deprecated and one should just use GLMakie (or CairoMakie, WGLMakie) at this point?

What about AbstractPlotting, should that be mentioned explicitly in the build script?

Makie.jl bundled GLMakie.jl and AbstractPlotting.jl before backends reexported AbstractPlotting.
Therefore, Makie.jl is equivalent to GLMakie.jl now, except it tends to fall behind on compat bounds and is only dragged along for compatibility.

All backends have AbstractPlotting as a dependency anyway, so you can’t avoid it.

Creating the sysimage itself is also very slow, at least in my case. I think we also need a sysimage for the PackageCompiler itself :grinning:.