Docker Community Forums

Share and learn in the Docker community.

Running PHP built in server


(Oshdev) #1

Hey,

I wanted to quickly create a simple PHP-based container, but it turned out to be a blocker for me…
Not sure what’s causing the following Dockerfile to fail:

FROM php
ENV APP_DIR /var/www/app
ENV APPLICATION_ENV development
RUN mkdir -p $APP_DIR
WORKDIR $APP_DIR
EXPOSE 80
VOLUME $APP_DIR
CMD ["php", "-S", "0.0.0.0:80", "-t", "./public", "./public/index.php"]

It builds fine, but when I run it: docker run -d --name phpd -v "$PWD":/var/www/app -p 80:80 phpd it exists straight away and what I get is:

CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS                     PORTS               NAMES
9a6b7dd84805        phpd                "php -S 0.0.0.0:80 -t"   2 seconds ago       Exited (1) 2 seconds ago                       phpd

Note how the command ends with -t and nothing after that.

Any clues what could be causing that?

On a side note if instead of detached I run interactive shell and execute php -S 0.0.0.0:80 -t ./public /public/index.php the container works perfectly fine…


(Oshdev) #2

Solved! I managed to solve it a couple days ago, but just know I thought I must post it if you’re struggling with it too.

TL;DR: don’t use relative paths!

The “php -S 0.0.0.0:80 -t” command presented was a false lead - it seems every command is truncated for a neater display only, but actually full command is begin run.
Docker logs didn’t show anything meaningful and nothing that I could find in a websearch (after all PHP build in server is not supposed to be used for anything serious and it’s quite under-documented).
The actual cause of the server failing to start is relative path when running docker.
I tried with the following in the docker file:

CMD ["php", "-S", "0.0.0.0:80", "-t", "./public", "./public/index.php"]

and I tried running like this:

docker run -d -v "$PWD":/var/www/app -p 80:80 IMAGE_TAG php -S 0.0.0.0:80 -t ./public ./public/index.php

but the results were the same.
After building the image, I was still able to make it work if done like this:

docker run -it -v "$PWD":/var/www/app -p 80:80 IMAGE_TAG bash

and then from within the container:

php -S 0.0.0.0:80 -t ./public ./public/index.php

but obviously this is not something I was looking for.

After experimenting with various stuff, it just came to me that the reason for failing were the relative paths when invoking php server.

Here’s the working php deamon is I call it for jokes:

FROM php

ENV APP_DIR /app
ENV APPLICATION_ENV development

WORKDIR $APP_DIR
VOLUME $APP_DIR

RUN php -r "copy('https://getcomposer.org/installer', 'composer-setup.php');    \
    \$sig = file_get_contents('https://composer.github.io/installer.sig');      \
    if (trim(\$sig) === hash_file('SHA384', 'composer-setup.php')) exit(0);     \
    echo 'ERROR: Invalid installer signature' . PHP_EOL;                        \
    unlink('composer-setup.php');                                               \
    exit(1);"                                                                   \
 && php composer-setup.php -- --filename=composer --install-dir=/usr/local/bin  \
 && rm composer-setup.php

EXPOSE 80

CMD ["php", "-S", "0.0.0.0:80", "-t", "/app/public", "/app/public/index.php"]

Then I just docker build -t phpd . and start it up

docker run -d -p 80:80 -v "$PWD":/app --name my_project phpd

and it works great.

I hope this helps ;]