DLang is notoriously ugly when it comes to complilation (note: that's my opinion, you can disagree and still benefit from this). Handling compiler and DUB versions is not that easy.
Fortunately, we can freeze these versions and encapsulate the compilation process in an OCI container.
This repo is intended to be forked, then tweaked for your needs. Out of the box you get simplest structure for DUB, README (here we are, aren't we?), LICENSE (MIT by default, so fork away and relicense as you wish), Dockerfile (you probably won't need to touch it) and couple of utility scripts.
As said, you probably won't touch it. It will copy the whole repo to the container
derived from dmd image, build the project, then copy the executable to another
image. That way we have rich compilation directory, but a neat, single executable
in the runtime. The executable is stored in /dapp
directory (which is also
the WORKDIR). The executable name is taken as APP_NAME
build argument with no
default. If you don't provide it manually, it will go bonkers; OTOH if
you use the following scripts, they will handle naming for you.
Currently the base image is
dlangchina/dlang-dmd:2.097.1
. It is derived from sid Debian, which sorta matters when describing scripts.
There are 2 scripts:
./build.sh TAG
./extract.sh TAG
The former will take the Dockerfile in the current directory and build it. Default Dockerfile was described above. After building, newly created image will be tagged with the argument.
The latter will spin up a container for the tag passed as an argument and copy the executable out of it into current directory. That executable should be... well, executable on your host right after the script exits.
Both scripts use APP_NAME
envvar to control the executable name. By default
it is simply app
. Unfortunately, installing jq on Debian is an overkill just
to extract the name from dub. Keeping the name in dub.json
and the one you
use as an APP_NAME
envvar is your job.
There are some more envvars that these scripts use:
build.sh
APP_NAME
- well, duh
IMAGE_BUILD
- command used to build an image from Dockerfile; expects to be docker drop-in
- defaults to
docker build
extract.sh
APP_NAME
- well, duh
CONTAINER_CREATE
,CONTAINER_RM
- in the same fashion, docker drop-in replacements with default of
docker create
anddocker rm
respectively
- in the same fashion, docker drop-in replacements with default of
FILE_CP
- used to copy file between a running container and host
- defaults to
docker cp
MAKE_NAME
- used to generate a container name; it doesn't need to satisfy any interface, it will simply be executed within shell and its stdout will be the container name
- defaults to
date +%s
(epoch number)
export APP_NAME=my-app
export TAG=$APP_NAME:0.0.42-SNAPSHOT
./build.sh $TAG
./extract.sh $TAG
./APP_NAME
export APP_NAME=my-app
export TAG=$APP_NAME:0.0.42-SNAPSHOT
./build.sh $TAG``
docker run $TAG