├── Makefile.sample ├── composer.json ├── .env.dist ├── nginx ├── Dockerfile └── conf.d │ └── symfony.conf.dist ├── php ├── conf.d │ └── custom.ini ├── entrypoint.sh └── Dockerfile ├── CONTRIBUTING.md ├── LICENSE ├── docker-compose.yml ├── README.md └── Makefile /Makefile.sample: -------------------------------------------------------------------------------- 1 | # Project specific variables 2 | DOCKER_PATH := ./docker 3 | PROJECT_PATH := /var/www/html 4 | 5 | # Retrieve the Makefile used to manage the Docker environment 6 | export COMPOSE_FILE := $(DOCKER_PATH)/docker-compose.yml 7 | include $(DOCKER_PATH)/Makefile 8 | -------------------------------------------------------------------------------- /composer.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "ajardin/docker-symfony", 3 | "description": "Docker environment that meets Symfony requirements", 4 | "license": "MIT", 5 | "authors": [ 6 | { 7 | "name": "Alexandre Jardin", 8 | "email": "info@ajardin.fr" 9 | } 10 | ] 11 | } 12 | -------------------------------------------------------------------------------- /.env.dist: -------------------------------------------------------------------------------- 1 | DOCKER_PHP_IMAGE=symfony_php_xdebug 2 | DOCKER_MOUNT_POINT=.. 3 | 4 | ##### BLACKFIRE 5 | BLACKFIRE_PORT=8707 6 | BLACKFIRE_LOG_LEVEL=4 7 | BLACKFIRE_SERVER_ID= 8 | BLACKFIRE_SERVER_TOKEN= 9 | BLACKFIRE_CLIENT_ID= 10 | BLACKFIRE_CLIENT_TOKEN= 11 | 12 | ##### POSTGRES 13 | POSTGRES_USER=symfony 14 | POSTGRES_PASSWORD=YourPwdShouldBeLongAndSecure! 15 | POSTGRES_DB=docker 16 | -------------------------------------------------------------------------------- /nginx/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM nginx:1.15-alpine 2 | 3 | # Install HTTPS requirements 4 | RUN \ 5 | apk add --no-cache --virtual .build-deps \ 6 | openssl && \ 7 | mkdir -p /etc/nginx/ssl && \ 8 | openssl req -subj '/CN=localhost' -days 365 -x509 -newkey rsa:4096 -nodes \ 9 | -keyout /etc/nginx/ssl/server.key -out /etc/nginx/ssl/server.crt && \ 10 | apk del .build-deps 11 | 12 | WORKDIR /var/www/html/ 13 | -------------------------------------------------------------------------------- /php/conf.d/custom.ini: -------------------------------------------------------------------------------- 1 | [core] 2 | date.timezone = UTC 3 | session.auto_start = Off 4 | short_open_tag = Off 5 | SMTP = maildev 6 | smtp_port = 25 7 | realpath_cache_size = 4096K 8 | realpath_cache_ttl = 600 9 | 10 | [opcache] 11 | opcache.enable_file_override = On 12 | opcache.interned_strings_buffer = 16 13 | opcache.max_accelerated_files = 20000 14 | opcache.memory_consumption = 256 15 | opcache.revalidate_freq = 0 16 | opcache.validate_timestamps = On 17 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing 2 | We would love to receive your help to make this Docker environment for Symfony better! 3 | 4 | Feel free to open an [issue](https://github.com/ajardin/docker-symfony/issues) if you run into any problem, or send 5 | a pull request (see bellow) with your contribution. 6 | 7 | ## Code of Conduct 8 | The code of conduct is described in [`CODE_OF_CONDUCT.md`](CODE_OF_CONDUCT.md). 9 | 10 | ## How to contribute 11 | :construction: 12 | -------------------------------------------------------------------------------- /php/entrypoint.sh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env sh 2 | set -euo pipefail 3 | 4 | if [[ $(php -r "echo (int) extension_loaded('blackfire');") -eq 1 ]]; then 5 | cat << CONFIG > "${PHP_INI_DIR}"/conf.d/blackfire.ini 6 | blackfire.agent_socket=tcp://blackfire:${BLACKFIRE_PORT} 7 | blackfire.agent_timeout=5 8 | blackfire.log_file=/var/log/blackfire.log 9 | blackfire.log_level=${BLACKFIRE_LOG_LEVEL} 10 | blackfire.server_id=${BLACKFIRE_SERVER_ID} 11 | blackfire.server_token=${BLACKFIRE_SERVER_TOKEN} 12 | CONFIG 13 | fi 14 | 15 | # Allow the Symfony application to write inside volumes 16 | mkdir -p /var/www/html/var/ && chown -R www-data /var/www/html/var/ 17 | 18 | exec "$@" 19 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2018 Alexandre Jardin 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /docker-compose.yml: -------------------------------------------------------------------------------- 1 | version: "3.4" 2 | 3 | services: 4 | blackfire: 5 | image: blackfire/blackfire:latest 6 | env_file: .env 7 | depends_on: 8 | - php 9 | 10 | maildev: 11 | image: djfarrelly/maildev:latest 12 | env_file: .env 13 | depends_on: 14 | - php 15 | ports: 16 | - 1080:80 17 | 18 | nginx: 19 | build: nginx 20 | env_file: .env 21 | ports: 22 | - 443:443 23 | volumes: 24 | - ${DOCKER_MOUNT_POINT}:/var/www/html:rw,delegated 25 | # Custom configuration 26 | - ./nginx/conf.d/custom.conf:/etc/nginx/conf.d/symfony.conf:ro 27 | depends_on: 28 | - php 29 | tty: true 30 | 31 | php: 32 | build: 33 | context: ./php 34 | target: ${DOCKER_PHP_IMAGE} 35 | env_file: .env 36 | volumes: 37 | - ${DOCKER_MOUNT_POINT}:/var/www/html:rw,delegated 38 | # Avoid heavy I/O workloads on bind-mounted volumes 39 | - /var/www/html/var/cache 40 | - /var/www/html/var/log 41 | # Custom configuration 42 | - ./php/conf.d/custom.ini:/usr/local/etc/php/conf.d/custom.ini:ro 43 | # SSH keys 44 | - ~/.ssh:/root/.ssh:ro 45 | tty: true 46 | 47 | postgres: 48 | image: postgres:10-alpine 49 | env_file: .env 50 | ports: 51 | - 5432:5432 52 | volumes: 53 | - postgres:/var/lib/postgresql/data 54 | tty: true 55 | 56 | volumes: 57 | postgres: {} 58 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Docker for Symfony [![License: MIT](https://img.shields.io/badge/License-MIT-blue.svg)](https://opensource.org/licenses/MIT) 2 | This repository allows the creation of a Docker environment that meets 3 | [Symfony requirements](https://symfony.com/doc/current/reference/requirements.html). 4 | 5 | **What you will find here is an environment designed to simplify the development workflow when working with a Symfony 6 | application. Thus, some services or configurations are not suitables for a production usage.** 7 | 8 | ## Architecture 9 | ![Architecture overview](docs/architecture.png "Architecture") 10 | 11 | ## Services 12 | * `blackfire`: [blackfire/blackfire:latest](https://hub.docker.com/r/blackfire/blackfire/) image (application profiling). 13 | * `maildev`: [djfarrelly/maildev:latest](https://hub.docker.com/r/djfarrelly/maildev/) (emails testing). 14 | * `nginx`: [nginx:1.15-alpine](nginx/Dockerfile) custom image with HTTPS (web server). 15 | * `php`: [php:7.2-fpm-alpine](php/Dockerfile) custom image with additional extensions and Composer. 16 | * `postgres`: [postgres:10-alpine](https://hub.docker.com/_/postgres/) image (database). 17 | 18 | And more to come... 19 | 20 | ## Documentation 21 | > In order to make things more readable, and maintainable, the documentation has been migrated to 22 | the [repository Wiki](https://github.com/ajardin/docker-symfony/wiki). Where you will find all details about the 23 | installation process along the available instructions for the day-to-day work. 24 | -------------------------------------------------------------------------------- /nginx/conf.d/symfony.conf.dist: -------------------------------------------------------------------------------- 1 | server { 2 | listen 443 ssl http2; 3 | listen [::]:443 ssl http2; 4 | 5 | server_name symfony.localhost; 6 | root /var/www/html/public; 7 | 8 | ssl on; 9 | ssl_certificate /etc/nginx/ssl/server.crt; 10 | ssl_certificate_key /etc/nginx/ssl/server.key; 11 | 12 | location / { 13 | # try to serve file directly, fallback to index.php 14 | try_files $uri /index.php$is_args$args; 15 | } 16 | 17 | location ~ ^/index\.php(/|$) { 18 | fastcgi_pass php:9000; 19 | fastcgi_split_path_info ^(.+\.php)(/.*)$; 20 | include fastcgi_params; 21 | 22 | # When you are using symlinks to link the document root to the 23 | # current version of your application, you should pass the real 24 | # application path instead of the path to the symlink to PHP 25 | # FPM. 26 | # Otherwise, PHP's OPcache may not properly detect changes to 27 | # your PHP files (see https://github.com/zendtech/ZendOptimizerPlus/issues/126 28 | # for more information). 29 | fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name; 30 | fastcgi_param DOCUMENT_ROOT $realpath_root; 31 | # Prevents URIs that include the front controller. This will 404: 32 | # http://domain.tld/index.php/some-path 33 | # Remove the internal directive to allow URIs like this 34 | internal; 35 | } 36 | 37 | # return 404 for all other php files not matching the front controller 38 | # this prevents access to other php files you don't want to be accessible. 39 | location ~ \.php$ { 40 | return 404; 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /php/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM php:7.2-fpm-alpine as symfony_php 2 | LABEL maintainer="Alexandre Jardin " 3 | 4 | # Install Symfony requirements 5 | RUN \ 6 | apk add --no-cache \ 7 | freetype-dev \ 8 | git \ 9 | icu-libs \ 10 | libjpeg-turbo-dev \ 11 | libpng-dev \ 12 | postgresql-libs \ 13 | ssmtp \ 14 | yarn \ 15 | zlib-dev && \ 16 | apk add --no-cache --virtual .build-deps \ 17 | $PHPIZE_DEPS \ 18 | icu-dev \ 19 | postgresql-dev && \ 20 | docker-php-ext-configure gd --with-freetype-dir=/usr/include/ --with-jpeg-dir=/usr/include/ && \ 21 | docker-php-ext-install \ 22 | intl \ 23 | gd \ 24 | opcache \ 25 | pdo_pgsql \ 26 | zip && \ 27 | perl -pi -e "s/mailhub=mail/mailhub=maildev/" /etc/ssmtp/ssmtp.conf && \ 28 | apk del .build-deps 29 | 30 | # Install Composer globally 31 | ENV COMPOSER_ALLOW_SUPERUSER 1 32 | RUN \ 33 | curl -sS https://getcomposer.org/installer | php && \ 34 | mv composer.phar /usr/local/bin/composer && \ 35 | composer self-update --preview 36 | 37 | # Install custom entrypoint 38 | COPY entrypoint.sh /usr/local/bin/docker-custom-entrypoint 39 | RUN chmod 777 /usr/local/bin/docker-custom-entrypoint 40 | CMD ["php-fpm"] 41 | ENTRYPOINT ["docker-custom-entrypoint"] 42 | 43 | # ====================================================================================================================== 44 | FROM symfony_php as symfony_php_blackfire 45 | RUN \ 46 | curl -sS https://packages.blackfire.io/binaries/blackfire-php/1.23.1/blackfire-php-alpine_amd64-php-72.so \ 47 | --output $(php -r "echo ini_get('extension_dir');")/blackfire.so && \ 48 | docker-php-ext-enable blackfire 49 | # ====================================================================================================================== 50 | 51 | # ====================================================================================================================== 52 | FROM symfony_php as symfony_php_xdebug 53 | RUN \ 54 | apk add --no-cache --virtual .build-deps $PHPIZE_DEPS && \ 55 | yes "" | pecl install xdebug && \ 56 | docker-php-ext-enable xdebug 57 | # ====================================================================================================================== 58 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | SELF_DIR := $(dir $(lastword $(MAKEFILE_LIST))) 2 | PHP_SERVICE := docker-compose exec php sh -c 3 | 4 | # Define a static project name that will be prepended to each service name 5 | export COMPOSE_PROJECT_NAME := symfony 6 | 7 | # This Makefile is designed to be extended by another Makefile located in your project directory. 8 | # ==> https://github.com/ajardin/docker-symfony/wiki/Makefile 9 | 10 | # Create configuration files needed by the environment 11 | SETUP_ENV := $(shell (test -f $(SELF_DIR).env || cp $(SELF_DIR).env.dist $(SELF_DIR).env)) 12 | SETUP_SERVER := $(shell (test -f $(SELF_DIR)nginx/conf.d/custom.conf || cp $(SELF_DIR)nginx/conf.d/symfony.conf.dist $(SELF_DIR)nginx/conf.d/custom.conf)) 13 | 14 | # Extract environment variables needed by the environment 15 | export DOCKER_PHP_IMAGE := $(shell grep DOCKER_PHP_IMAGE $(SELF_DIR).env | awk -F '=' '{print $$NF}') 16 | export DOCKER_MOUNT_POINT := $(shell grep DOCKER_MOUNT_POINT $(SELF_DIR).env | awk -F '=' '{print $$NF}') 17 | 18 | ## 19 | ## ---------------------------------------------------------------------------- 20 | ## Environment 21 | ## ---------------------------------------------------------------------------- 22 | ## 23 | 24 | backup: ## Backup the "postgres" volume 25 | docker run --rm \ 26 | --volumes-from $$(docker-compose ps -q postgres) \ 27 | -v $$(pwd):/backup \ 28 | busybox sh -c "tar cvf /backup/backup.tar /var/lib/postgresql/data" 29 | 30 | build: ## Build the environment 31 | docker-compose build 32 | 33 | cache: ## Flush the Symfony cache 34 | $(PHP_SERVICE) "bin/console cache:clear" 35 | 36 | composer: ## Install Composer dependencies from the "php" container 37 | $(PHP_SERVICE) "composer install --optimize-autoloader --prefer-dist --working-dir=$(PROJECT_PATH)" 38 | 39 | logs: ## Follow logs generated by all containers 40 | docker-compose logs -f --tail=0 41 | 42 | logs-full: ## Follow logs generated by all containers from the containers creation 43 | docker-compose logs -f 44 | 45 | nginx: ## Open a terminal in the "nginx" container 46 | docker-compose exec nginx sh 47 | 48 | php: ## Open a terminal in the "php" container 49 | docker-compose exec php sh 50 | 51 | ps: ## List all containers managed by the environment 52 | docker-compose ps 53 | 54 | restore: ## Restore the "postgres" volume 55 | docker run --rm \ 56 | --volumes-from $$(docker-compose ps -q postgres) \ 57 | -v $$(pwd):/backup \ 58 | busybox sh -c "tar xvf /backup/backup.tar /var/lib/postgresql/data" 59 | docker-compose restart postgres 60 | 61 | start: ## Start the environment 62 | docker-compose build 63 | docker-compose up -d --remove-orphans 64 | 65 | stats: ## Print real-time statistics about containers ressources usage 66 | docker stats $(docker ps --format={{.Names}}) 67 | 68 | stop: ## Stop the environment 69 | docker-compose stop 70 | 71 | yarn: ## Install npm dependencies from the "php" container 72 | $(PHP_SERVICE) "yarn install --cwd=$(PROJECT_PATH)" 73 | 74 | .PHONY: backup build cache composer logs logs-full nginx php ps restore start stats stop yarn 75 | 76 | .DEFAULT_GOAL := help 77 | help: 78 | @grep -E '(^[a-zA-Z_-]+:.*?##.*$$)|(^##)' $(MAKEFILE_LIST) \ 79 | | sed -e 's/^.*Makefile://g' \ 80 | | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[32m%-30s\033[0m %s\n", $$1, $$2}' \ 81 | | sed -e 's/\[32m##/[33m/' 82 | .PHONY: help 83 | --------------------------------------------------------------------------------