Report a bug
If you spot a problem with this page, click here to create a GitHub issue.
Improve this page
Quickly fork, edit online, and submit a pull request for this page. Requires a signed-in GitHub account. This works well for small changes. If you'd like to make larger changes you may want to consider using a local clone.

Docker and OCI images

dlang-dockerized is a community project that packages D compilers as OCI images. These can be used with OCI-compliant container engines — such as Docker Podman or Kubernetes.

Note: OCI stands for Open Container Initiative.

Quick Start

Docker

docker run --init --rm -it -v .:/src ghcr.io/dlang-dockerized/dmd:latest dmd

Podman

podman run --init --rm -it -v .:/src ghcr.io/dlang-dockerized/dmd:latest dmd

Common CLI flags

The provided command runs the container image for dmd from ghcr.io. It mounts the current working directory . as volume (-v) under /src in the container.

--rm instructs the container engine to automatically remove the container and any anonymous unnamed volume associated with the container when it exits.

-it is actually a combination of the flags -i and and requests an interactive session — even if detached — with a pseudo-TTY.

Given that most applications are not designed to be run as PID 1, using --init the container engine can be instructed to inject a tiny init system which takes care of the signal handling requirements for PID 1 of the Linux kernel as well as reaping orphaned zombie processes.

Further information can be found in the corresponding manuals:

Containerfiles

Container images are built from so-called Containerfiles — also known as Dockerfiles when used with Docker.

These Containerfiles are compiled from templates and meta data.

A repository providing pre-rendered Containerfiles can be found at: https://github.com/dlang-dockerized/containerfiles

The source template files as well as the template engine are located in the packaging repository: https://github.com/dlang-dockerized/packaging

Documentation for the format of Containerfiles can be found over there: https://github.com/podman-container-tools/container-libs/blob/main/common/docs/Containerfile.5.md

Packaged software

Note: Please note that not all software listed above is available across all image versions. This applies to images providing legacy compiler versions in particular.

Compiler versions

dlang-dockerized aims to package the latest compilers as well as “relevant” legacy versions.

To select a specific version of a container image, append a version prefix to the image name.

Note: The prefix latest refers to the latest stable release of the corresponding image.
# Containerfile

# latest stable release
FROM ghcr.io/dlang-dockerized/dmd:latest

# latest release of the 2.100.x branch (→ 2.100.2)
FROM ghcr.io/dlang-dockerized/dmd:2.100

# 2.100.0 release
FROM ghcr.io/dlang-dockerized/dmd:2.100.0

Images are rebuilt from time to time in order to ship dependency updates and similar.

For legacy versions of the bundled software it may be necessary to apply custom patches and/or backports in order prior to building. These modifications can be found in the patches subfolder in the packaging repository.

Base images

A base image is the start of all Containerfiles. It serves as the base of the container and as such provides a runtime environment.

A common convention is to append a suffix to the tag of the container image that consists of an alias referring to the base image.

Maintained versions and images

The maintenance policy of dlang-dockerized is outlined in the MAINTENANCE document of the project. It can be found at https://github.com/dlang-dockerized/packaging/blob/main/MAINTENANCE.md.

Note: : Keep in mind, this is work done by volunteers.

Container registries

Container images are pushed to two container registries: The registry to pull an image from is selected by prepending the corresponding registry host and vendor name to the image name:
Note: At the time of writing, ghcr.io is the recommended registry to pull these images from.
Note: Docker defaults to docker.io; allowing users to omit that prefix.
Best practice is, however, to explicitly specify the source registry of an image. This ensures compatibility across container engines and user configurations.

Tips and tricks

Debugging with LLDB

At the time of writing, due to a limitation in LLDB, seccomp confinement needs to be turned off for the debugger to work.

docker run --security-opt seccomp=unconfined -it dlang-dockerized/ldc:latest lldb /src/my-app

For further information check out: https://github.com/llvm/llvm-project/issues/61899

Issue tracker

See: https://github.com/dlang-dockerized/packaging/issues

Packaging your own app as container image

The following examples outline how one can build and package their own application using OCI containers. They are meant to be used as a starting point only. Downstream users are expected to adjust them accordingly to fit their requirements and tune them to their liking.

Note: The D community is usually more than happy to help you with getting your Containerfile set up and running.

No build system

  1. Navigate into the root folder of your project.
  2. Create a file named Dockerfile (no file extension) in that directory.
  3. Copy and paste the following template:
    # build stage
    FROM ghcr.io/dlang-dockerized/dmd:latest AS build-stage
    COPY . /d-project
    RUN dmd -inline -O -i -I=/d-project/src /d-project/src/app.d -of=/my-d-app
    
    # runtime stage
    FROM docker.io/debian:latest
    COPY --from=build-stage /my-d-app /usr/local/bin/my-d-app
    CMD ["/usr/local/bin/my-d-app"]
    
  4. Adjust as needed.
  5. Run docker build . --tag my-d-app:v1.0.0 to build the container image.

Using DUB

  1. Navigate into the folder of your project where your DUB recipe (i.e. dub.json or dub.sdl) is located.
  2. Specify a targetPath and a targetName in your DUB recipe. While this step is optional, it will make it easier to copy the right binary into the runtime stage later.
  3. Create a file named Dockerfile (no file extension) in that directory.
  4. Copy and paste the following template:
    # build stage
    FROM ghcr.io/dlang-dockerized/dmd:latest AS build-stage
    COPY . /d-project
    RUN dub build --build=plain
    
    # runtime stage
    FROM docker.io/debian:latest
    COPY --from=build-stage /targetPath/targetName /usr/local/bin/my-d-app
    CMD ["/usr/local/bin/my-d-app"]
    
  5. Adjust as needed.
  6. Run docker build . --tag my-d-app:v1.0.0 to build the container image.