Docker for PHP Developers: Local Development Setup
Learn Docker from basics to advanced concepts with practical examples for PHP and Laravel development, including multi-container setups and production deployment.
StalkTechie
Author
Docker for PHP Developers: Local Development Setup
Docker simplifies PHP development by providing consistent, isolated environments across machines. This guide covers Docker basics, containerizing PHP apps (especially Laravel), multi-service setups with Docker Compose, volume management, optimization, and tips for production deployment. Ideal for Laravel, Symfony, or plain PHP projects in 2025 with Docker 27.x+.
Docker Basics and Installation
Docker uses containers (lightweight VMs) to package apps with dependencies.
- Images: Blueprints (e.g., php:8.3-fpm).
- Containers: Running instances.
- Volumes: Persistent data.
- Networks: Communication between containers.
Install Docker Desktop (Windows/Mac) or Docker Engine (Linux). Enable WSL2 on Windows.
# Test installation
docker --version
docker run hello-world
Key commands: docker build, docker run, docker ps, docker exec, docker compose.
Containerizing a Simple PHP App
Create a Dockerfile for a basic PHP script.
# Dockerfile
FROM php:8.3-cli # Base image
WORKDIR /app
COPY . /app
CMD ["php", "index.php"]
<?php // index.php
echo "Hello from Docker PHP!";
Build and run:
docker build -t my-php-app .
docker run --rm my-php-app
For web apps, use php:8.3-apache or fpm with Nginx.
Docker for Laravel: Multi-Container Setup
Use Docker Compose for app, web server, DB, and cache.
Directory Structure
my-laravel-app/
├── app/ (Laravel code)
├── docker/
│ ├── php/Dockerfile
│ ├── nginx/nginx.conf
│ └── mysql/my.cnf
├── docker-compose.yml
PHP Dockerfile
FROM php:8.3-fpm
# Install dependencies
RUN apt-get update && apt-get install -y \
libpng-dev libjpeg-dev zip unzip git \
&& docker-php-ext-install pdo_mysql gd
# Composer
COPY --from=composer:latest /usr/bin/composer /usr/bin/composer
WORKDIR /var/www
COPY app /var/www
RUN composer install --optimize-autoloader --no-dev
RUN chown -R www-data:www-data /var/www
CMD ["php-fpm"]
Nginx Config
server {
listen 80;
index index.php;
server_name localhost;
root /var/www/public;
location / {
try_files $uri $uri/ /index.php?$query_string;
}
location ~ \.php$ {
fastcgi_pass php:9000;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
}
}
docker-compose.yml
version: '3.9'
services:
php:
build: ./docker/php
volumes:
- ./app:/var/www
networks: [app-network]
nginx:
image: nginx:latest
ports: ["8000:80"]
volumes:
- ./app:/var/www
- ./docker/nginx/nginx.conf:/etc/nginx/conf.d/default.conf
depends_on: [php]
networks: [app-network]
mysql:
image: mysql:8.0
environment:
MYSQL_ROOT_PASSWORD: secret
MYSQL_DATABASE: laravel
MYSQL_USER: laravel
MYSQL_PASSWORD: secret
volumes:
- db-data:/var/lib/mysql
ports: ["3306:3306"]
networks: [app-network]
redis:
image: redis:alpine
networks: [app-network]
networks:
app-network:
driver: bridge
volumes:
db-data:
Start: docker compose up -d. Access app at http://localhost:8000. Run Artisan: docker compose exec php php artisan migrate.
For Laravel env: Copy .env.example, set DB_HOST=mysql.
Volume Management and Data Persistence
- Bind mounts:
./app:/var/wwwfor code syncing. - Named volumes: For DB to persist data.
- Anonymous volumes: For temp caches.
Cleanup: docker volume prune. Backup: docker compose down -v.
Optimization and Best Practices
- Multi-Stage Builds: Separate build/runtime for smaller images.
FROM composer as builder
COPY . /app
RUN composer install --no-dev
FROM php:8.3-fpm
COPY --from=builder /app /var/www
healthcheck: { test: ["CMD", "curl", "-f", "http://localhost"] }.USER 1000. Scan images with Trivy.env_file: .env.Debugging and Tools
- Logs:
docker compose logs -f php. - Shell:
docker compose exec php bash. - Xdebug: Add to Dockerfile
pecl install xdebug && docker-php-ext-enable xdebug; configure in php.ini. - VS Code: Docker extension for building/running.
- Portainer: Web UI for management.
Production Deployment
- Docker Swarm/Kubernetes: For orchestration. Use
docker stack deploy. - CI/CD: GitHub Actions: Build image, push to Docker Hub/ECR, deploy to ECS/Heroku.
- Reverse Proxy: Add Traefik or Nginx Proxy Manager.
- SSL: Use Let's Encrypt with Certbot in containers.
- Scaling:
docker compose up --scale php=3. - Monitoring: Prometheus + Grafana; watch CPU/memory with
docker stats.
Platforms: Render, Fly.io, or AWS ECS for easy PHP Docker deploys.
Common Issues and Fixes
- File Permissions: Use
chmod -R 777 storageor www-data user. - Port Conflicts: Change host ports in compose.
- Windows Path Issues: Use Linux containers.
- Composer Slow: Cache volumes
~/.composer:/tmp/composer.
Advanced: Custom Images and Extensions
Build PHP with extensions like Redis: pecl install redis && docker-php-ext-enable redis.
For Node frontend: Add node service in compose.
Docker streamlines PHP dev - consistent envs reduce "works on my machine" issues. Start with Sail (Laravel's Docker setup: curl -s https://laravel.build/app | bash) for quickstarts. Scale to orchestration as needed!