Search code examples
python-3.xmacosdockertkinter

How to run tkinter inside a docker container on MacBook Pro?


I'm trying to run a python GUI application that uses tkinter module inside a docker container on my MacBook Pro.

So I installed XQuartz and followed this tutorial to run a simple tkinter program inside a docker container.

And here's the error message I got

Traceback (most recent call last):
  File "/app/tkinter_app.py", line 4, in <module>
    root_window = tk.Tk()
  File "/usr/local/lib/python3.8/tkinter/__init__.py", line 2270, in __init__
    self.tk = _tkinter.create(screenName, baseName, className, interactive, wantobjects, useTk, sync, use)
_tkinter.TclError: couldn't connect to display "/private/tmp/com.apple.launchd.knFz0UzqxP/org.xquartz:0"

The value of my DISPLAY environment variable is /private/tmp/com.apple.launchd.knFz0UzqxP/org.xquartz:0.

Anyone knows how to solve this error?

Here's the Dockerfile in the tutorial

# Slim version of Python
FROM python:3.8.12-slim

# Download Package Information
RUN apt-get update -y

# Install Tkinter
RUN apt-get install tk -y

# Commands to run Tkinter application
CMD ["/app/tkinter_app.py"]
ENTRYPOINT ["python3"]

Line 4 of /app/tkinter_app.py is root_window = tk.Tk().

My MacOS version is 11.6.1.


Solution

  • I made a little docker image with xeyes in it to test X11 clients with the XQuartz X11 server on my Mac using this as my Dockerfile:

    # Base Image
    FROM alpine:latest
    
    RUN apk update && \
        apk add --no-cache xeyes
    
    # Set a working directory
    WORKDIR /work
    
    # Start a shell by default
    CMD ["ash"]
    

    And then I built it like this:

    docker build -t setchell/xeyes .
    

    And I run it with this:

    # Prerequisites
    #   brew cask install xquartz
        
    # Set your Mac IP address
    IP=$(/usr/sbin/ipconfig getifaddr en0)
    
    # Allow connections from Mac to XQuartz
    /opt/X11/bin/xhost + "$IP"
    
    # Run container
    docker run -it -e DISPLAY="${IP}:0" -v /tmp/.X11-unix:/tmp/.X11-unix setchell/xeyes
    

    And once in the container, I just run:

    xeyes
    

    And here is the result:

    enter image description here


    Note that I had to start XQuartz on my Mac, go to "Preferences" and then "Security" and tick (check) both options and restart my Mac before the above procedure. See diagram here.