DEV Community

Cover image for Using Docker for Slim 4 application development environment
Cherif Bouchelaghem
Cherif Bouchelaghem

Posted on • Updated on

Using Docker for Slim 4 application development environment

In the first part of the series we write a small Slim 4 application to know how the framework works, however in real world applications we need to know how to deal with more complicated problems instead of printing a message on a web page.

I believe, as software developers we need to prepare the work environment first and because we have a number of environments where the code we wrote will be running we need to be sure that those environment characteristics are common to minimize the number of surprises.

Also, as team members, having the same development environment could be helpful to ensure we are all having the same results without any impact from the local environment.

Fortunately, Docker can help to achieve those goals.

Create docker directory

Create a new directory named docker, this directory will contain Docker containers definitions and doesn’t have to be named docker:

$ mkdir docker
Enter fullscreen mode Exit fullscreen mode

Define a PHP 8 container

1- Inside the docker directory, add a new subdirectory named php:

$ mkdir -p docker/php
Enter fullscreen mode Exit fullscreen mode

2- Create a new Dockerfile (yes without extension) file

touch docker/php/Dockerfile
Enter fullscreen mode Exit fullscreen mode

Open the php Dockerfile and add the following instructions:

FROM php:8.1-fpm

RUN apt update \
    && apt install -y zlib1g-dev g++ git libicu-dev zip libzip-dev zip libpq-dev \
    && docker-php-ext-configure pgsql -with-pgsql=/usr/local/pgsql \
    && docker-php-ext-install intl opcache pdo pdo_pgsql \
    && pecl install apcu \
    && docker-php-ext-enable apcu \
    && docker-php-ext-configure zip \
    && docker-php-ext-install zip

WORKDIR /var/www/slim_app

RUN curl -sS https://getcomposer.org/installer | php -- --install-dir=/usr/local/bin --filename=composer

RUN git config --global user.email "you@example.com" \
    && git config --global user.name "Your Name"
Enter fullscreen mode Exit fullscreen mode

Note: Make sure to replace git credentials in the last two lines with your git credentials

The instructions above will scaffold a PHP container from a PHP 7.4 FPM image and:

  • Install PHP extension that our Slim application depends on
  • Sets the working directory of the container to /var/www/slim_app
  • Install composer

Define a NGINX web server container

Unlike the PHP image, only NGINX default configuration is needed inside a subdirectory in docker directory:

Add new nginx directory:

$ mkdir -p docker/nginx
Enter fullscreen mode Exit fullscreen mode

Add the default configuration file:

$ touch docker/nginx/default.conf
Enter fullscreen mode Exit fullscreen mode

Edit docker/nginx/default.conf with the following:

server {

    listen 80;
    index index.php;
    server_name localhost;
    root /var/www/slim_app/public;
    error_log /var/log/nginx/project_error.log;
    access_log /var/log/nginx/project_access.log;

    location / {
        try_files $uri /index.php$is_args$args;
    }

    location ~ ^/index\\.php(/|$) {
        fastcgi_pass php:9000;
        fastcgi_split_path_info ^(.+\\.php)(/.*)$;
        include fastcgi_params;

        fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
        fastcgi_param DOCUMENT_ROOT $realpath_root;

        fastcgi_buffer_size 128k;
        fastcgi_buffers 4 256k;
        fastcgi_busy_buffers_size 256k;

        internal;
    }

    location ~ \\.php$ {
        return 404;
    }

}
Enter fullscreen mode Exit fullscreen mode

This is the simplest NGINX required configuration to run a PHP application, note that it maps fastcgi_pass to port 9000 in the PHP container we defined previously.

Let’s compose the containers images

To use the PHP and NGINX defined containers we need to create docker-compose.yml in the root folder of the application:

version: "3.8"

services:
  php:
    container_name: slim_php
    build:
      context: ./docker/php
    ports:
      - '9000:9000'
    volumes:
      - .:/var/www/slim_app

  nginx:
    container_name: slim_nginx
    image: nginx:stable-alpine
    ports:
      - '8080:80'
    volumes:
      - .:/var/www/slim_app
      - ./docker/nginx/default.conf:/etc/nginx/conf.d/default.conf
    depends_on:
      - php
Enter fullscreen mode Exit fullscreen mode

Let see what we have here for the PHP container:

  • Unlike the NGINX container configuration, PHP container doesn’t have an image key but a build context in order to use the docker/php/Dockerfile to build the container.
  • Port 9000 of the computer is mapped to 9000 of the container
  • Volumes is declared to store the data generated by the container, in the case of this example it will store the Slim application code in the project.

For NGINX

  • nginx:stable-alpine will be pulled from the docker-hub to build the container.
  • The port 8080 of the computer is mapped to port 80 of the container.
  • Declare the required volumes to persist the NGINX default configuration file and the PHP code for the application.

Build the containers

Run the following command to build the containers:

$ docker-compose up -d --build
Enter fullscreen mode Exit fullscreen mode

Once containers are successfully built the terminal should print message like the following screenshot:

Alt Text

To make sure that the containers are up and running open the Docker Desktop app, it should shows that the containers are running like in the screenshot below:

Alt Text

It is possible to use the command line to know the status of the containers:

$ docker ps
Enter fullscreen mode Exit fullscreen mode

Should print something like:
Alt Text

Now if you visit the URL localhost:8080, put the port you configured for NGINX, should run the Slim application we built in the first part.

GitHub repository has the code in this part in development-environment-part-2.

Top comments (3)

Collapse
 
xvillagran profile image
Xuan Villagran

Great post, saved me lots of time! Thank you

Collapse
 
mrmalsan profile image
MaLSan dos Santos

Hey! Nice article!
I'm facing some problems! I download your code from Github, compose the containers according to article's instructions (docker-compose up -d --build) and start to create my API inside that. It have worked fine for the first time. But, since a remove the containers (and images) e tried to compose it again, i'm facing an intriguing problem: the "apt update" command (on Dokerfile) simply do not work animore! It returns an error message like:

E: Problem executing scripts APT::Update::Post-Invoke 'rm -f /var/cache/apt/archives/.deb /var/cache/apt/archives/partial/.deb /var/cache/apt/*.bin || true'

6 21.17 E: Sub-process returned an error code


executor failed running [/bin/sh -c apt update && apt install -y zlib1g-dev g++ git libicu-dev zip libzip-dev zip libpq-dev && docker-php-ext-configure pgsql -with-pgsql=/usr/local/pgsql && docker-php-ext-install intl opcache pdo pdo_pgsql && pecl install apcu && docker-php-ext-enable apcu && docker-php-ext-configure zip && docker-php-ext-install zip]: exit code: 100
ERROR: Service 'php' failed to build : Build failed

In order to Troubleshoot this, i tried without success:

To use "apt-get" instead "apt";
To call "docker compose" instead of "docker-compose";
To use root privileges;
To restart, to reset to factory default and to reinstall the Docker Desktop (4.1.0 on Macos Catalina);
To execute "docker run -it php:8.1-fpm" and so execute "apt update" on the container. That shows the sabe message I reproduce above.
Would you, please, have any hint about this problem? I would really appreciate any help! Thanks in advance!

Collapse
 
nicolaspereira profile image
Nicolas Rocha Pereira

Hey! Thanks for your article, I have a question!

In my GET routes it is working normally but for my POST routes I am getting the following error:

502 Bad Gateway

How can I solve?

Tks