Monday, April 11, 2016

Running GUI Apps in Docker on Mac OS X

I've been trying to figure out how to run GUI apps in a Docker container on my Mac running OS X El Capitan. As a developer, I try out many different software packages and configurations. I would love to be able to try out certain things in a well-contained environment where I won't leave bits and pieces lying around if something doesn't work or if I get bored with the package. I have also been enamored with using Docker for development environments to make them portable and self-contained. After many searches and experiments, I finally stumbled on what I needed to do.

I am using the Docker Toolbox to run Docker on my Mac. I have also used Boot2Docker, but the Docker Toolbox experience is a little smoother. Either option will work to get Docker containers running on your system.

One of the required pieces I had to install was XQuartz. This is an X11 windowing system that runs on the Mac. I was originally worried about installing this package, concerned that it would interfere with the X11 windowing system built into OS X. So far, I haven't had any trouble with it.

To try out a GUI app, I wanted a basic Linux container with an obvious GUI app that is not installed on my Mac. I created a basic Dockerfile defining an image based on the latest distribution of Ubuntu. I then install Firefox into the image. The image starts up at a bash prompt, which allows me to run programs. Here is that docker file:

FROM ubuntu:latest

RUN apt-get update && apt-get install -y firefox

CMD /bin/bash

Getting Docker to create an image and run a container based on that image was pretty straightforward with the Docker Toolbox for Mac OS X. The hardest part was trying to get the running container to bind the DISPLAY environment variable to the XQuartz server. This link finally broke things open for me. A comment from slobo on January 22, 2015 has the secret sauce. In an xterm window started under XQuartz, run the command

socat TCP-LISTEN:6000,reuseaddr,fork UNIX-CLIENT:\"$DISPLAY\"
Then, when starting the container, set the DISPLAY environment variable to the IP of the Docker virtual machine. (This IP address is usually a 192.168.x.x value.) I found this IP address on my Mac by typing
ifconfig
and locating the vboxnetn entry (where n is 0 - 9). For me, it looked like:

Using the IP address 192.168.99.1, I ran the following command to start a running container:

docker run -it -e DISPLAY=192.168.99.1:0 firefox
(firefox is the image name for the Ubuntu image running Firefox I defined with the Dockerfile above.) When I got to the bash prompt inside the running container, I ran Firefox, and the UI appeared like another window in OS X!

I am just starting my journey with Docker, but I'm excited about the possibilities it offers.

UPDATE:

Benny Cornelissen (@whieee) has a blog post that does a really good job integrating XQuartz and the instantiation of containers into the bash shell.

No comments:

Post a Comment