EMG Portal in Docker

It is possible to run EMG Portal in a Docker container, which simplifies and automates the installation procedure. Below we provide a starting point to how this can be done. The idea is to use a Dockerfile to build a local image, which is then run by a shell script.

The files below assume that an EMG Portal database already exists and is populated with the necessary data, e.g,. the initial users.

Building the Docker image

First, we need a Dockerfile. This version is based on Ubuntu 18.04, which uses PHP 7.2.

# syntax=docker/dockerfile:experimental
FROM ubuntu:18.04 as emgportal-ubuntu-18
LABEL maintainer="user@example.se"
RUN apt-get update
RUN DEBIAN_FRONTEND=noninteractive apt-get install -y tzdata
RUN \
        apt-get install -y \
        apache2 \
        bzip2 \
        less \
        libmysqlclient20 \
        mlocate \
        net-tools \
        ntp \
        ntpdate \
        php \
        php-curl \
        php-dev \
        php-mbstring \
        php-mysql \
        php-pdo \
        php-pear \
        php-xml \
        vim \
        wget \
        zsh && \
        apt-get clean
RUN sed -i.sed \
  -e 's/^memory_limit.*/memory_limit = 512M/' \
  -e 's/^max_execution_time.*/max_execution_time = 600/' \
  /etc/php/7.2/cli/php.ini
WORKDIR /usr/local
RUN \
        wget https://downloads.ioncube.com/loader_downloads/ioncube_loaders_lin_x86-64.tar.gz && \
        tar xzf ioncube_loaders_lin_x86-64.tar.gz && \
        rm -f ioncube_loaders_lin_x86-64.tar.gz && \
        echo "zend_extension = /usr/local/ioncube/ioncube_loader_lin_7.2.so" > /etc/php/7.2/mods-available/01-ioncube.ini && \
        ln -s /etc/php/7.2/mods-available/01-ioncube.ini /etc/php/7.2/apache2/conf.d/ && \
        ln -s /etc/php/7.2/mods-available/01-ioncube.ini /etc/php/7.2/cli/conf.d/ && \
        a2enmod rewrite
WORKDIR /var/www/html
RUN \
        wget -O emgportal.tar.gz https://nordicmessaging.se/wp-content/uploads/emgportal-eval-7.php && \
        mkdir emgportal
WORKDIR emgportal
RUN \
        tar xzf ../emgportal.tar.gz && \
        rm -rf install && \
        mkdir assets protected/runtime && \
        chmod 777 assets protected/runtime protected/config && \
        cp htaccess.sample .htaccess && \
        sed -i.sed \
                -e 's/.*RewriteBase/RewriteBase/' \
                .htaccess && \
        cp emgportal.conf /etc/apache2/conf-available && \
        ln -s ../conf-available/emgportal.conf /etc/apache2/conf-enabled
COPY cmd-ubuntu18.sh /opt/cmd.sh
CMD [ "/opt/cmd.sh" ]
EXPOSE 80 443

The script cmd-ubuntu18.sh performs some updates, and then starts the web server.

#!/bin/sh
cd /var/www/html/emgportal/protected/config
cp db.php.tmpl db.php
sed -i.sed \
        -e "s/_DBHOST_/$EMG_DBHOST/" \
        -e "s/_DBNAME_/$EMG_DBNAME/" \
        -e "s/_DBUSERNAME_/$EMG_DBUSERNAME/" \
        -e "s/_DBPASSWORD_/$EMG_DBPASSWORD/" \
        db.php
cp main.php.sample main.php
ntpd
exec apache2 -DFOREGROUND

To build the image, we use the following command.

docker build \
        --target emgportal-ubuntu-18 \
        -t emgportal \
        .

Running the Docker image

For this example, the database is running in its own docker container. It uses the docker network “portal-net” which provides a link between EMG Portal and the database. You can of course use other solutions that fit your situation better.

The configuration values are stored in a file on the Docker host. We will use the name emgportal.env.

EMG_DBHOST=portal-mysql
EMG_DBNAME=portal
EMG_DBUSERNAME=portal
EMG_DBPASSWORD=portal

APACHE_RUN_DIR=/var/www/html
APACHE_PID_FILE=/var/run/apache2/pid
APACHE_RUN_USER=www-data
APACHE_RUN_GROUP=www-data
APACHE_LOG_DIR=/var/log/apache2

To run the Docker image, we use a command such as the one below.


docker run --rm -ti \
        --privileged \
        --network portal-net \
        --name emgportal \
        --env-file emgportal.env \
        --mount type=bind,source=`pwd`/emgportal_eval.txt,target=/var/www/html/emgportal/protected/emgportal_eval.txt
        -p 8080:80 \
        -p 8443:443 \
        emgportal

Additional configurations

You will likely want to make additional configurations. There are several ways to do this.

  1. Add more steps to the Dockerfile, copying in your local files on top of the downloaded EMG Portal files. Any changes to your local files requires the image to be rebuilt and then restarted. This would be a good solution when adding your own layout, images, etc.
  2. Let the cmd.sh script update the files in-place, as is done with the db.php file above. Any changes will require the container to be restarted.
  3. Use bind mounts to link files on the host with files in the container, as is done with emgportal_eval.txt. Changes on the host will then take effect in the running container immediately.

Files can be copied out of the container using a command such as “docker cp emgportal:/path/to/the/file /local/file/name”, after using “docker exec emgportal ls” etc.