Skip to content

Instantly share code, notes, and snippets.

@themightychris
Created September 24, 2019 22:55
Show Gist options
  • Star 3 You must be signed in to star a gist
  • Fork 4 You must be signed in to fork a gist
  • Save themightychris/51a63a1c2bf6f3be82c9e85481106fa0 to your computer and use it in GitHub Desktop.
Save themightychris/51a63a1c2bf6f3be82c9e85481106fa0 to your computer and use it in GitHub Desktop.
nginx + PHP composite Docker container
#
# Multi-Stage Docker build:
# Laravel 5.8 + PHP73 + Postgres || MySQL
#
# @link https://laravel.com/docs/5.8
# @link https://hub.docker.com/_/php
# @link https://hub.docker.com/_/mysql
# @link https://hub.docker.com/_/postgres
#
#
# Stage 1 - Prep App's PHP Dependencies
#
FROM composer:1.8 as vendor
COPY database/ database/
COPY composer.json composer.json
COPY composer.lock composer.lock
RUN composer install \
--ignore-platform-reqs \
--no-interaction \
--no-plugins \
--no-scripts \
--prefer-dist \
--quiet
# end Stage 1 #
#
# Stage 2 - Prep App's Frontend CSS & JS
#
FROM node:10.15-jessie as frontend
RUN mkdir -p /app/public
COPY package.json webpack.mix.js yarn.lock /app/
COPY resources/assets/ /app/resources/assets/
COPY resources/js/ /app/resources/js/
COPY resources/sass/ /app/resources/sass/
WORKDIR /app
RUN yarn install --silent \
&& yarn production
# end Stage 2 #
#
# Stage 3 - Build Final App
#
FROM php:7.3-fpm-alpine3.8
# write version information into container
ARG SOURCE_COMMIT
LABEL SOURCE_COMMIT="${SOURCE_COMMIT}"
ENV SOURCE_COMMIT="${SOURCE_COMMIT}"
ARG SOURCE_TAG
LABEL SOURCE_TAG="${SOURCE_TAG}"
ENV SOURCE_TAG="${SOURCE_TAG}"
# add cli tools
RUN apk update \
&& apk upgrade \
&& apk add bash \
&& apk add nano \
&& apk add nginx \
&& apk add npm
# silently install 'docker-php-ext-install' extensions
RUN set -x
# Database option: postgres
RUN apk add --no-cache postgresql-dev
RUN docker-php-ext-install pdo_pgsql bcmath > /dev/null
# Database option: mysql
# RUN docker-php-ext-install pdo_mysql bcmath > /dev/null
# copy app source folder (less .dockerignore exclusions)
COPY . /srv/app
# add app dependencies from multi-stage builds
COPY --from=vendor /app/vendor/ /srv/app/vendor/
COPY --from=frontend /app/public/js/ /srv/app/public/js/
COPY --from=frontend /app/public/css/ /srv/app/public/css/
COPY --from=frontend /app/public/fonts/ /srv/app/public/fonts/
COPY --from=frontend /app/public/mix-manifest.json /srv/app/public/mix-manifest.json
# misc...
WORKDIR /srv/app
# nginx - nginx app permissions
RUN mkdir -p /run/nginx
RUN chown -R www-data:www-data *
# nging - nginx permissions for laravel storage & cache
RUN adduser nginx www-data \
&& chgrp -R www-data storage bootstrap/cache \
&& chmod -R 775 storage bootstrap/cache
# nginx - config file
COPY ./docker/nginx/default.conf /etc/nginx/conf.d/default.conf
# cleanup apk
RUN rm -rf /var/cache/apk/*
# cleanup docker
RUN rm -rf /srv/app/docker
# bash alias for 'php artisan'
RUN touch ~/.bashrc \
&& echo 'source ~/.bash_profile' >> ~/.bashrc \
&& echo 'alias art="php artisan"' >> ~/.bash_profile \
&& echo 'alias watch="npm run watch &"' >> ~/.bash_profile
ENV LOG_CHANNEL=stderr
# docker entrypoint
COPY ./docker/php73/entrypoint.sh /entrypoint.sh
CMD ["/entrypoint.sh"]
# end Stage 3 #
#!/usr/bin/env bash
# inspired by https://github.com/formapro/docker-nginx-php-fpm/blob/master/base/entrypoint.sh
## start nginx and php in the background, kill both on exit
TRAPPED_SIGNAL=false
echo 'Starting NGINX';
nginx -g 'daemon off;' 2>&1 &
NGINX_PID=$!
echo 'Starting PHP-FPM';
php-fpm 2>&1 &
PHP_FPM_PID=$!
trap "TRAPPED_SIGNAL=true; kill -15 $NGINX_PID; kill -15 $PHP_FPM_PID;" SIGTERM SIGINT
## initialize config cache
php artisan config:cache
## watch nginx and php in an ongoing loop
while :
do
kill -0 $NGINX_PID 2> /dev/null
NGINX_STATUS=$?
kill -0 $PHP_FPM_PID 2> /dev/null
PHP_FPM_STATUS=$?
if [ "$TRAPPED_SIGNAL" = "false" ]; then
if [ $NGINX_STATUS -ne 0 ] || [ $PHP_FPM_STATUS -ne 0 ]; then
if [ $NGINX_STATUS -eq 0 ]; then
kill -15 $NGINX_PID;
wait $NGINX_PID;
fi
if [ $PHP_FPM_STATUS -eq 0 ]; then
kill -15 $PHP_FPM_PID;
wait $PHP_FPM_PID;
fi
exit 1;
fi
else
if [ $NGINX_STATUS -ne 0 ] && [ $PHP_FPM_STATUS -ne 0 ]; then
exit 0;
fi
fi
# trigger laravel scheduler every 60s
php artisan schedule:run --verbose --no-interaction &
sleep 60
done
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment