A complete Docker-based local development environment supporting both WordPress and Laravel projects with automatic project setup, intelligent project detection, and streamlined development workflows.
- Traefik: Upgraded to v3.5 (latest stable release)
- phpMyAdmin: Updated to latest version for improved security
- Adminer: Updated to latest version for better performance
- PHP: Already using 8.4 (latest stable) in all Docker images
- Composer: Using version 2.8 for better dependency management
- MariaDB: Continues with 11.6 LTS for stability
- Redis: Using 7.4 Alpine for minimal footprint
- Elasticsearch/Kibana: 7.17.25 with full security features enabled
- Docker - Containerization platform for consistent development environments
- Docker Compose - Multi-container Docker applications
- Traefik v3.5 - Modern reverse proxy and load balancer for automatic routing (latest stable)
- MariaDB 11.6 - Latest LTS database server (MySQL-compatible)
- PHP 8.4 - Latest PHP version with improved performance and features
- Nginx - Web server (for Laravel projects)
- Apache - Web server (for WordPress projects)
- Composer 2.8 - PHP dependency management
- GitHub Authentication - For private repository access
- Mailpit - Modern email testing and development tool
- phpMyAdmin - Database administration interface (latest version)
- Adminer - Lightweight database administration tool (latest version)
- Elasticsearch 7.17.25 - Search and analytics engine with security enabled
- Kibana 7.17.25 - Elasticsearch data visualization with authentication
- WP-CLI - Command-line interface for WordPress
- Redis 7.4 - In-memory data structure store (for Laravel projects)
- WordPress - Latest stable version (6.5+) with WP-CLI integration
- Laravel - Modern PHP framework with full feature support
- Docker Desktop - For Windows/macOS users
- Docker Engine - For Linux users
- Bash Shell - For script execution
- Git - Version control (optional but recommended)
- Ruby 3.4+ - For DIP (Docker Interaction Process) support (optional but recommended)
The setup script automatically detects your project type and configures the environment. It also generates a dip.yml file for simplified Docker commands.
cd wp-local/docker
./setup.sh <project-name>Examples:
# For WordPress project
./setup.sh smartyapp
# For Laravel project
./setup.sh smartylaravelWhat the setup script does:
- Detects project type (WordPress or Laravel)
- Configures environment variables
- Auto-generates dip.yml with project-specific settings
- Starts Docker containers
- Sets up database and dependencies
DIP (Docker Interaction Process) provides a simplified interface for Docker operations. Navigate to your project directory first:
# Navigate to your project
cd www/<project-name>
# Common commands
dip up # Start all services
dip down # Stop all services
dip logs # View logs
dip restart # Restart services
dip clean # Stop and remove volumesWordPress-specific:
dip wp plugin list # Run WP-CLI commands
dip shell # Access PHP container
dip db # Access database CLILaravel-specific:
dip artisan migrate # Run Artisan commands
dip composer install # Run Composer
dip npm install # Run NPM commands
dip test # Run testsIf you prefer manual control:
cd wp-local/docker
# For WordPress
docker-compose -f docker-compose.wordpress.yml up -d
# For Laravel
docker-compose -f docker-compose.laravel.yml up -dDIP (Docker Interaction Process) simplifies Docker commands and provides a cleaner workflow.
macOS:
# Install Ruby 3.4+ via Homebrew (if not already installed)
brew install ruby
# Add Ruby to your PATH in ~/.zshrc or ~/.bash_profile
export PATH="/opt/homebrew/opt/ruby/bin:$PATH"
export PATH="/opt/homebrew/lib/ruby/gems/3.4.0/bin:$PATH"
# Reload shell
source ~/.zshrc # or source ~/.bash_profile
# Install DIP gem
gem install dip
# Verify installation
dip versionLinux:
# Install Ruby 3.4+ via package manager
# Ubuntu/Debian:
sudo apt-get install ruby-full
# Fedora/RHEL:
sudo dnf install ruby
# Install DIP gem
gem install dip
# Verify installation
dip versionAutomatic Generation: When you create a new project using the setup scripts, a dip.yml file is automatically generated in your project directory with the correct configuration for your project type (WordPress or Laravel).
The auto-generated dip.yml file includes:
- Project-specific environment variables (database credentials, domain, etc.)
- Pre-configured commands for common tasks (up, down, logs, etc.)
- Framework-specific commands (WP-CLI for WordPress, Artisan for Laravel)
- Container access commands (shell, database CLI, etc.)
Example projects with dip.yml:
- www/smartyapp/dip.yml - WordPress configuration
- www/smartylaravel/dip.yml - Laravel configuration
Manual creation: If you need to create a dip.yml file manually, templates are available at:
- docker/templates/dip.wordpress.yml - WordPress template
- docker/templates/dip.laravel.yml - Laravel template
Navigate to your project directory and use simple commands:
cd www/your-project
dip ls # List all available commands
dip up # Start services
dip down # Stop servicesThe setup uses separate environment templates for different project types:
docker/
βββ .env # Auto-generated by setup.sh
βββ .env.wordpress # WordPress environment template
βββ .env.laravel # Laravel environment template
βββ docker-compose.wordpress.yml
βββ docker-compose.laravel.yml
βββ Dockerfile.wordpress
βββ Dockerfile.laravel
βββ setup.sh # Automated setup script
Environment files (.env) contain configuration variables that customize your Docker environment:
- Project-specific settings - APP_ID, PROJECT_DOMAIN, database credentials
- Version control - PHP version, MariaDB version, phpMyAdmin version
- Authentication - GitHub token for private repository access
- Database configuration - Database name, user, password
- Template Selection: Setup script detects project type (WordPress/Laravel)
- Environment Generation: Copies appropriate template (
.env.wordpressor.env.laravel) - Variable Substitution: Replaces placeholders with your project name
- Container Launch: Uses the generated
.envfile for Docker configuration
| Variable | Purpose | Example |
|---|---|---|
APP_ID |
Project identifier | smartyapp |
PROJECT_DOMAIN |
Local domain | smartyapp.test |
DB_NAME |
Database name | smartyapp |
DB_USER |
Database user | smartyapp |
DB_PASSWORD |
Database password | smartyapp |
PHP_VERSION |
PHP Docker image version | 8.4-apache |
MARIADB_VERSION |
MariaDB version | 11.6 |
GITHUB_AUTH_TOKEN |
GitHub authentication | ghp_xyz123... |
wp-local/
βββ docker/
β βββ .env # Auto-generated environment
β βββ .env.wordpress # WordPress template
β βββ .env.laravel # Laravel template
β βββ docker-compose.wordpress.yml # WordPress services
β βββ docker-compose.laravel.yml # Laravel services
β βββ Dockerfile.wordpress # WordPress container
β βββ Dockerfile.laravel # Laravel container
β βββ setup.sh # Automated setup script
β βββ nginx.conf # Nginx configuration
β βββ default.conf # Default site configuration
β βββ supervisord.conf # Process management
βββ www/
β βββ smartyapp/ # WordPress project
β β βββ wp/ # WordPress core files
β β βββ mysql/ # Database files
β β βββ elasticsearch/ # Search index data
β β βββ composer.json # WordPress dependencies
β βββ smartylaravel/ # Laravel project
β βββ app/ # Laravel application
β βββ public/ # Public web directory
β βββ mysql/ # Database files
β βββ redis/ # Redis data
β βββ elasticsearch/ # Search index data
β βββ composer.json # Laravel dependencies
βββ README.md # This documentation
The setup script automatically detects your project type:
- Looks for
wp-config.phporwp/wp-config.php - Uses
docker-compose.wordpress.yml - Mounts
../www/{project}/wp:/var/www/html
- Looks for
artisanfile andcomposer.json - Uses
docker-compose.laravel.yml - Mounts
../www/{project}:/var/www/html
| Service | WordPress URL | Laravel URL | Description |
|---|---|---|---|
| Your Site | http://smartyapp.test |
http://smartylaravel.test |
Your application |
| phpMyAdmin | http://phpmyadmin.test |
http://phpmyadmin.test |
Database management (full-featured) |
| Adminer | http://adminer.test |
http://adminer.test |
Database management (lightweight) |
| Mailpit | http://mailpit.test |
http://mailpit.test |
Email testing and debugging |
| Kibana | http://kibana-smartyapp.test |
http://kibana-smartylaravel.test |
Elasticsearch visualization |
| Elasticsearch | http://localhost:9201 |
http://localhost:9200 |
Search and analytics API |
| Traefik Dashboard | http://localhost:8080 |
http://localhost:8080 |
Proxy management |
# From wp-local/docker/ directory
./setup.sh <project-name>- Project Detection: Automatically detects WordPress or Laravel
- Environment Setup: Copies and configures appropriate
.envfile - Variable Substitution: Updates project-specific variables
- Container Management: Stops existing containers and starts new ones
- Dependency Installation: Installs Composer dependencies (Laravel)
- Laravel Setup: Runs key generation and migrations (Laravel projects)
# From wp-local/docker/ directory
./setup.sh smartylaravel
βΉοΈ Setting up Docker environment for project: smartylaravel
β
Detected Laravel project
β
Using Laravel environment configuration
β
Environment configured for smartylaravel (laravel)
π Project started successfully!
βΉοΈ Project URL: http://smartylaravel.test
βΉοΈ phpMyAdmin: http://phpmyadmin.test
βΉοΈ Installing Laravel dependencies...With DIP (from project directory):
cd www/your-project
dip up # Start services
dip down # Stop services
dip logs # View logs
dip restart # Restart servicesTraditional Docker Compose (from docker directory):
cd wp-local/docker
docker-compose -f docker-compose.wordpress.yml up -d
docker-compose -f docker-compose.wordpress.yml down
docker-compose -f docker-compose.wordpress.yml logs -f
docker-compose -f docker-compose.wordpress.yml restartBefore switching between WordPress and Laravel, always clear all containers to avoid conflicts:
# From any directory
# Stop all running containers
docker stop $(docker ps -q)
# Remove all containers
docker rm $(docker ps -a -q)
# Remove all networks (optional)
docker network prune -f
# Remove all volumes (optional - this will delete databases!)
docker volume prune -f
# Complete cleanup (removes images, containers, networks, volumes)
docker system prune -a -f --volumes# From wp-local/docker/ directory
# Start WordPress environment
docker-compose -f docker-compose.wordpress.yml up -d
# Stop WordPress environment
docker-compose -f docker-compose.wordpress.yml down
# Stop WordPress with volume removal
docker-compose -f docker-compose.wordpress.yml down -v
# Rebuild WordPress containers
docker-compose -f docker-compose.wordpress.yml up --build -d
# View WordPress logs
docker-compose -f docker-compose.wordpress.yml logs -f# From wp-local/docker/ directory
# Start Laravel environment
docker-compose -f docker-compose.laravel.yml up -d
# Stop Laravel environment
docker-compose -f docker-compose.laravel.yml down
# Stop Laravel with volume removal
docker-compose -f docker-compose.laravel.yml down -v
# Rebuild Laravel containers
docker-compose -f docker-compose.laravel.yml up --build -d
# View Laravel logs
docker-compose -f docker-compose.laravel.yml logs -fWhen switching from WordPress to Laravel (or vice versa):
# Method 1: Stop specific project first
# From wp-local/docker/ directory
docker-compose -f docker-compose.wordpress.yml down
docker-compose -f docker-compose.laravel.yml up -d
# Method 2: Use the setup script (recommended)
# From wp-local/docker/ directory
./setup.sh smartylaravel # Automatically stops WordPress and starts Laravel
# Method 3: Complete cleanup (if having issues)
# From any directory
docker stop $(docker ps -q)
docker rm $(docker ps -a -q)
# From wp-local/docker/ directory
./setup.sh smartylaravelWith DIP (from project directory):
cd www/smartylaravel
dip shell # Access Laravel container
dip artisan migrate # Run migrations
dip tinker # Open Tinker
dip composer install # Install dependencies
dip npm install # Install frontend dependencies
dip test # Run tests
dip queue # Start queue workerTraditional Docker Commands:
# From any directory
# Access Laravel container
docker exec -it laravel_smartylaravel bash
# Run Laravel commands
docker exec -it laravel_smartylaravel php artisan migrate
docker exec -it laravel_smartylaravel php artisan tinker
docker exec -it laravel_smartylaravel composer installWith DIP (from project directory):
cd www/smartyapp
dip shell # Access PHP container
dip wp user list # List WordPress users
dip wp plugin list # List plugins
dip wp core update # Update WordPress core
dip composer install # Install dependencies
dip db # Access database CLITraditional Docker Commands:
# From any directory
# Access WordPress container
docker exec -it php_smartyapp bash
# Run WP-CLI commands
docker exec -it php_smartyapp wp --allow-root user list
docker exec -it php_smartyapp wp --allow-root plugin listYou can create project-specific environment files:
# From wp-local/docker/ directory
# Copy template
cp .env.laravel .env.myproject
# Edit variables
nano .env.myproject
# Use custom environment
cp .env.myproject .env
docker-compose -f docker-compose.laravel.yml up -dAdd variables to your environment template:
# From wp-local/docker/ directory
# Edit .env.laravel file
nano .env.laravel
# Add these variables:
APP_DEBUG=true
APP_ENV=local
MAIL_DRIVER=smtp- Base:
php:8.4-apache - Services: Apache, PHP, WP-CLI
- Volumes: WordPress files, database, uploads, elasticsearch data
- Networking: Traefik routing
- Base:
php:8.4-fpm - Services: Nginx, PHP-FPM, Supervisor
- Volumes: Laravel application, database, storage, elasticsearch data
- Networking: Traefik routing, Redis connection
- MariaDB 11.6: Database server
- Redis 7.4: Caching and sessions (Laravel)
- Traefik v3.5: Reverse proxy and SSL termination (latest stable)
- phpMyAdmin latest: Full-featured database management interface
- Adminer latest: Lightweight database administration tool
- Mailpit latest: Modern email testing and debugging
- Elasticsearch 7.17.25: Search and analytics engine with security enabled
- Kibana 7.17.25: Data visualization and monitoring with authentication
-
Containers from previous project still running:
# From any directory # Check what containers are running docker ps # Stop all containers docker stop $(docker ps -q) # Remove all containers docker rm $(docker ps -a -q) # From wp-local/docker/ directory # Then start your new project ./setup.sh project-name
-
Port conflicts:
# From any directory # Check what's using port 80 sudo lsof -i :80 # Stop conflicting services sudo service apache2 stop sudo service nginx stop
-
Permission issues:
# From wp-local/ directory # Fix file permissions sudo chown -R $USER:$USER www/ # From any directory # Laravel storage permissions docker exec -it laravel_{project-name} chmod -R 755 storage/
-
Database connection errors:
# From wp-local/docker/ directory # Reset environment docker-compose down -v ./setup.sh project-name
-
Container build failures:
# From any directory # Clean Docker cache docker system prune -a # From wp-local/docker/ directory # Rebuild without cache docker-compose up --build --no-cache
-
WordPress containers still active when trying to start Laravel:
# From wp-local/docker/ directory # Quick fix docker-compose -f docker-compose.wordpress.yml down docker-compose -f docker-compose.laravel.yml up -d # Or use setup script (recommended) ./setup.sh smartylaravel
-
Database user doesn't exist error (Laravel):
# From any directory # If you get "Access denied for user 'projectname'" error docker exec db_{project-name} mysql -u root -proot -e "CREATE USER 'projectname'@'%' IDENTIFIED BY 'projectname';" docker exec db_{project-name} mysql -u root -proot -e "CREATE DATABASE IF NOT EXISTS projectname;" docker exec db_{project-name} mysql -u root -proot -e "GRANT ALL PRIVILEGES ON projectname.* TO 'projectname'@'%';" docker exec db_{project-name} mysql -u root -proot -e "FLUSH PRIVILEGES;" # Then run migrations docker exec laravel_{project-name} php artisan migrate --no-interaction
# From any directory
# Check container status
docker ps
# View container logs
docker logs container_name
# Check environment variables
docker exec -it container_name env
# Test database connection
docker exec -it db_{project-name} mysql -u root -p
# Check file permissions
docker exec -it container_name ls -la /var/www/htmlBoth tools are available for database management:
phpMyAdmin (http://phpmyadmin.test):
- Full-featured database administration
- WordPress-friendly interface
- Comprehensive import/export tools
- Plugin ecosystem
Adminer (http://adminer.test):
- Lightweight and fast
- Clean, modern interface
- Supports multiple database types
- Better performance for large datasets
# Access Adminer at http://adminer.test
# Login credentials:
# Server: db
# Username: root
# Password: root
# Database: [your-project-name]# Check Elasticsearch cluster health (with authentication)
curl -u elastic:changeme http://localhost:9200/_cluster/health?pretty
# Check cluster status (quick view)
curl -u elastic:changeme http://localhost:9200/_cat/health
# View all indices
curl -u elastic:changeme http://localhost:9200/_cat/indicesSecurity Enabled: Elasticsearch 7.17.25 with authentication enabled for Fleet and Agent integrations.
Default Credentials: Username: elastic, Password: changeme
# Install Laravel Scout for Elasticsearch
docker exec -it laravel_{project-name} composer require laravel/scout
docker exec -it laravel_{project-name} composer require matchish/laravel-scout-elasticsearch
# Configure in your Laravel .env
SCOUT_DRIVER=elasticsearch
ELASTICSEARCH_HOST=elasticsearch:9200
ELASTICSEARCH_USERNAME=elastic
ELASTICSEARCH_PASSWORD=changeme
# Create and sync searchable models
docker exec -it laravel_{project-name} php artisan scout:import "App\Models\Post"# Install ElasticPress plugin
docker exec -it php_{project-name} wp --allow-root plugin install elasticpress --activate
# Configure Elasticsearch endpoint in WordPress admin:
# Settings > ElasticPress > Settings
# Host: http://elasticsearch:9200
# Username: elastic
# Password: changeme
# Index content via WP-CLI
docker exec -it php_{project-name} wp --allow-root elasticpress index --setupAccess Kibana at http://kibana-{project-name}.test to:
- Monitor search performance
- Create data visualizations
- Analyze user search patterns
- Track application metrics
# Access Kibana with authentication
# URL: http://kibana-{project-name}.test
# Username: elastic
# Password: changeme
# View Kibana logs for debugging
docker logs kibana_{project-name}
# Check Elasticsearch connection from Kibana container
docker exec -it kibana_{project-name} curl -u elastic:changeme http://elasticsearch:9200/_cluster/health- Authentication Required: Login with username
elasticand passwordchangeme - Fleet Management: Now available for Elastic Agent integrations
- API Keys: Enabled for agent authentication (
xpack.security.authc.api_key.enabled=true) - Full Security: All Elasticsearch security features are active
# Check Elasticsearch status
curl http://localhost:9200/_cluster/health
# View all indices
curl http://localhost:9200/_cat/indices
# Search data directly
curl -X GET "localhost:9200/your_index/_search?pretty"# From any directory
# Optimize Laravel
docker exec -it laravel_{project-name} php artisan optimize
docker exec -it laravel_{project-name} php artisan config:cache
docker exec -it laravel_{project-name} php artisan route:cache
docker exec -it laravel_{project-name} php artisan view:cache# From any directory
# Enable object caching
docker exec -it php_{project-name} wp --allow-root plugin install redis-cache --activate
# Install Elasticsearch plugin for enhanced search
docker exec -it php_{project-name} wp --allow-root plugin install elasticpress --activate
# Optimize database
docker exec -it php_{project-name} wp --allow-root db optimizeMailpit replaces MailHog and provides modern email testing:
Access: http://mailpit.test
Features:
- Modern web interface
- Real-time email capture
- HTML email rendering
- Attachment handling
- Email search and filtering
Laravel Configuration:
# Already configured in docker-compose
MAIL_MAILER=smtp
MAIL_HOST=mailpit
MAIL_PORT=1025
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=nullWordPress Configuration:
- Install SMTP plugin or configure in wp-config.php
- SMTP Server: mailpit
- Port: 1025
- No authentication required
Testing Emails:
# Laravel - send test email
docker exec -it laravel_{project-name} php artisan tinker
# In tinker: Mail::raw('Test email', function($msg) { $msg->to('[email protected]')->subject('Test'); });
# WordPress - use WP-CLI
docker exec -it php_{project-name} wp --allow-root eval "wp_mail('[email protected]', 'Test Subject', 'Test message');"- Environment Files: Never commit
.envfiles to version control - Database Credentials: Use strong passwords in production
- GitHub Tokens: Use minimal required permissions
- Container Security: Regularly update base images
- Local Only: This setup is for local development only
- Firewall: Ensure Docker ports aren't exposed externally
- Backup: Regularly backup your project files and databases
Directory: wp-local/docker/
# Project 1 (WordPress)
./setup.sh myblog
# Visit: http://myblog.test
# Project 2 (Laravel)
./setup.sh myapi
# Visit: http://myapi.test
# Both projects run simultaneously
# Each has isolated database and environmentDirectory: any
Add custom domains to /etc/hosts:
# Edit hosts file
sudo nano /etc/hosts
# Add entries
127.0.0.1 custom-domain.test
127.0.0.1 another-project.testTraefik can be configured for SSL:
# In docker-compose files
labels:
- "traefik.http.routers.project.tls=true"
- "traefik.http.routers.project.rule=Host(`project.test`)"- Use the setup script for consistent environments
- Backup databases before major changes
- Use version control for your application code
- Test migrations before applying to production
- Monitor container logs for debugging
# WordPress
www/project/wp/ # WordPress core (don't edit)
www/project/wp/wp-content/themes/ # Custom themes
www/project/wp/wp-content/plugins/ # Custom plugins
# Laravel
www/project/app/ # Application logic
www/project/resources/ # Views and assets
www/project/database/migrations/ # Database migrations# From any directory
# Update WordPress core
docker exec -it php_{project-name} wp --allow-root core update
# Update plugins
docker exec -it php_{project-name} wp --allow-root plugin update --all
# Update themes
docker exec -it php_{project-name} wp --allow-root theme update --all# From any directory
# Update dependencies
docker exec -it laravel_{project-name} composer update
# Run migrations
docker exec -it laravel_{project-name} php artisan migrate
# Clear caches
docker exec -it laravel_{project-name} php artisan cache:clear# From wp-local/docker/ directory
# Pull latest images
docker-compose pull
# Rebuild containers
docker-compose up --build -dThis project follows Semantic Versioning and uses automated releases via semantic-release.
- Major (X.0.0): Breaking changes
- Minor (0.X.0): New features, backwards compatible
- Patch (0.0.X): Bug fixes, backwards compatible
Releases are automatically created when changes are pushed to the main branch. The version number is determined by analyzing commit messages following the Conventional Commits specification.
# Features (minor version bump)
feat(docker): add Redis service for caching
# Bug fixes (patch version bump)
fix: resolve MySQL connection timeout
# Breaking changes (major version bump)
feat(docker)!: upgrade to PHP 8.4For more details, see CONTRIBUTING.md.
We welcome contributions! Please follow our commit message conventions to ensure proper versioning:
- Use conventional commits format:
type(scope): description - Run
npm run commitfor an interactive commit experience - Create feature branches and submit pull requests
- Automated tests and releases run on merge to main
See CONTRIBUTING.md for detailed guidelines.
| Command | Description |
|---|---|
dip ls |
List all available commands |
dip up |
Start all services |
dip down |
Stop all services |
dip restart |
Restart all services |
dip logs |
View service logs |
dip clean |
Stop and remove volumes |
| Command | Description |
|---|---|
dip wp <command> |
Run WP-CLI commands |
dip shell |
Access PHP container shell |
dip db |
Access database CLI |
dip composer <command> |
Run Composer commands |
dip status |
Check WordPress installation status |
Examples:
dip wp plugin list
dip wp user create john [email protected] --role=editor
dip wp db export backup.sql| Command | Description |
|---|---|
dip artisan <command> |
Run Artisan commands |
dip shell |
Access Laravel container shell |
dip composer <command> |
Run Composer commands |
dip npm <command> |
Run NPM commands |
dip test |
Run Pest tests |
dip migrate |
Run database migrations |
dip queue |
Start queue worker |
dip tinker |
Open Laravel Tinker |
dip db |
Access database CLI |
dip redis |
Access Redis CLI |
Examples:
dip artisan make:model Post
dip composer require laravel/sanctum
dip npm run dev
dip test --filter UserTestπ Happy Development!
This environment supports both WordPress and Laravel development with automatic project detection, intelligent environment configuration, and streamlined workflows for modern PHP development.