I am currently working with elixir. It is a neat language, with a lot of good tooling. It’s rooted in the erlang world. A very useful tool to have some overview on the internals of the BEAM is the erlang observer.
Nowadays, the common workflow relies on containers. It is a very common issue to try to start graphical applications from within a container. Let’s prepare a playground
FROM elixir:1.10.4
ARG uid=1000
ARG gid=1000
RUN groupadd -g ${gid} alchymist \
&& useradd -u ${uid} -g alchymist alchymist \
&& mkdir -p /test \
&& chown alchymist:alchymist /test
USER alchymist
WORKDIR /test
ENTRYPOINT ["iex"]
CMD []
We can build it with
docker build --build-arg=uid=$(id -u) --build-arg=gid=$(id -g) -t alchymist:0 .
Let’s start normally
docker run --rm -ti alchymist:0
Trying to start the observer, we get an error
Erlang/OTP 22 [erts-10.7.2.2] [source] [64-bit] [smp:8:8] [ds:8:8:10] [async-threads:1] [hipe]
Interactive Elixir (1.10.4) - press Ctrl+C to exit (type h() ENTER for help)
iex(1)> :observer.start()
09:46:02: Error: Unable to initialize GTK+, is DISPLAY set properly?
{:error,
{{:einval, 'Could not initiate graphics'},
[
{:wxe_server, :start, 1, [file: 'wxe_server.erl', line: 65]},
{:wx, :new, 1, [file: 'wx.erl', line: 115]},
{:observer_wx, :init, 1, [file: 'observer_wx.erl', line: 107]},
{:wx_object, :init_it, 6, [file: 'wx_object.erl', line: 372]},
{:proc_lib, :init_p_do_apply, 3, [file: 'proc_lib.erl', line: 249]}
]}}
iex(2)>
The trick is to mount the needed files and pass the correct value for the environment variable DISPLAY.
docker run --rm \
-v $HOME/.Xauthority:$HOME/.Xauthority:rw \
-v /tmp/.X11-unix:/tmp/.X11-unix \
-e DISPLAY=$DISPLAY \
-ti alchymist:0
Starting the observer, we then succeed
Erlang/OTP 22 [erts-10.7.2.2] [source] [64-bit] [smp:8:8] [ds:8:8:10] [async-threads:1] [hipe] Interactive Elixir (1.10.4) - press Ctrl+C to exit (type h() ENTER for help) iex(1)> :observer.start() :ok iex(2)>
