Step 1: Project Structure
Create a directory structure that separates each Laravel application:
laravel-docker/
│
├── app1/ # Laravel App 1 using PHP 7.4
│ ├── laravel/ # Laravel application files
│
├── app2/ # Laravel App 2 using PHP 8.0
│ ├── laravel/ # Laravel application files
│
├── app3/ # Laravel App 3 using PHP 8.1
│ ├── laravel/ # Laravel application files
│
├── docker/
│ ├── php7.4/ # PHP 7.4 Docker configuration
│ │ └── Dockerfile
│ │
│ ├── php8.0/ # PHP 8.0 Docker configuration
│ │ └── Dockerfile
│ │
│ ├── php8.1/ # PHP 8.1 Docker configuration
│ │ └── Dockerfile
│
└── docker-compose.yml # Docker Compose configuration file
Step 2: Install Nginx on Your Host Machine
Install Nginx on your local machine using the appropriate command based on your operating system:
- Ubuntu/Debian:
sudo apt update sudo apt install nginx
- CentOS/RHEL:
sudo yum install epel-release sudo yum install nginx
- MacOS (Homebrew):
brew install nginx
Step 3: Configure Nginx
Edit the Nginx configuration file to connect with PHP running inside Docker containers. Create a server block in Nginx to point to the Dockerized PHP service.
Nginx Configuration (/etc/nginx/sites-available/laravel
):
# Configuration for App 1 using PHP 7.4
server {
listen 80;
server_name app1.localhost;
root /path/to/app1/laravel/public;
index index.php index.html index.htm;
location / {
try_files $uri $uri/ /index.php?$query_string;
}
location ~ \.php$ {
include fastcgi_params;
fastcgi_pass 127.0.0.1:9001; # PHP 7.4
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
}
location ~ /\.ht {
deny all;
}
}
# Configuration for App 2 using PHP 8.0
server {
listen 80;
server_name app2.localhost;
root /path/to/app2/laravel/public;
index index.php index.html index.htm;
location / {
try_files $uri $uri/ /index.php?$query_string;
}
location ~ \.php$ {
include fastcgi_params;
fastcgi_pass 127.0.0.1:9002; # PHP 8.0
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
}
location ~ /\.ht {
deny all;
}
}
# Configuration for App 3 using PHP 8.1
server {
listen 80;
server_name app3.localhost;
root /path/to/app3/laravel/public;
index index.php index.html index.htm;
location / {
try_files $uri $uri/ /index.php?$query_string;
}
location ~ \.php$ {
include fastcgi_params;
fastcgi_pass 127.0.0.1:9003; # PHP 8.1
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
}
location ~ /\.ht {
deny all;
}
}
Enable the configuration:
sudo ln -s /etc/nginx/sites-available/laravel /etc/nginx/sites-enabled/
sudo nginx -t
sudo systemctl restart nginx
Step 4: Create a Separate Docker Compose File for MySQL
Create a docker-compose.db.yml
file dedicated to MySQL.
docker-compose.db.yml
(For MySQL Service)
version: '3.8'
services:
# MySQL Service (shared by all apps)
mysql:
image: mysql:5.7
container_name: mysql
environment:
MYSQL_ROOT_PASSWORD: root
MYSQL_DATABASE: laravel
MYSQL_USER: laravel
MYSQL_PASSWORD: secret
volumes:
- db_data:/var/lib/mysql
ports:
- "3306:3306" # Expose MySQL port for connections from apps
volumes:
db_data:
Step 5: Configure Individual Docker Compose Files for Each App
Modify the docker-compose
files for each application to remove the MySQL service and connect them to the shared MySQL container.
docker-compose.app1.yml
(For App 1 – PHP 7.4)
version: '3.8'
services:
# PHP 7.4 Service for App 1
php7.4:
build:
context: ./docker/php7.4
container_name: php7.4
volumes:
- ./app1/laravel:/var/www/html
ports:
- "9001:9000" # Mapping port for PHP 7.4
depends_on:
- mysql # Ensure the PHP service waits for MySQL to be ready
networks:
- shared-network
networks:
shared-network:
external: true
docker-compose.app2.yml
(For App 2 – PHP 8.0)
version: '3.8'
services:
# PHP 8.0 Service for App 2
php8.0:
build:
context: ./docker/php8.0
container_name: php8.0
volumes:
- ./app2/laravel:/var/www/html
ports:
- "9002:9000" # Mapping port for PHP 8.0
depends_on:
- mysql # Ensure the PHP service waits for MySQL to be ready
networks:
- shared-network
networks:
shared-network:
external: true
docker-compose.app3.yml
(For App 3 – PHP 8.1)
version: '3.8'
services:
# PHP 8.1 Service for App 3
php8.1:
build:
context: ./docker/php8.1
container_name: php8.1
volumes:
- ./app3/laravel:/var/www/html
ports:
- "9003:9000" # Mapping port for PHP 8.1
depends_on:
- mysql # Ensure the PHP service waits for MySQL to be ready
networks:
- shared-network
networks:
shared-network:
external: true
Step 6: Create the Shared Network
To allow the services in different Docker Compose files to communicate, create an external Docker network named shared-network
. This network will connect the MySQL container with the PHP containers across different Compose files.
Create the shared network using the following command:
docker network create shared-network
Step 7: Update Laravel Environment Configuration
In each Laravel application’s .env
file, configure the database connection to use the shared MySQL service. Set the DB_HOST
to mysql
(the name of the MySQL service as defined in docker-compose.db.yml
).
Example .env
Configuration for Each App:
DB_CONNECTION=mysql
DB_HOST=mysql
DB_PORT=3306
DB_DATABASE=laravel
DB_USERNAME=laravel
DB_PASSWORD=secret
Step 8: Start the MySQL Container
First, bring up the MySQL service using its separate Docker Compose file:
docker-compose -f docker-compose.db.yml up -d
Step 9: Start Each Application
Start each Laravel application using its respective Docker Compose file:
- Start App 1 (PHP 7.4):
docker-compose -f docker-compose.app1.yml up -d
- Start App 2 (PHP 8.0):
docker-compose -f docker-compose.app2.yml up -d
- Start App 3 (PHP 8.1):
docker-compose -f docker-compose.app3.yml up -d
Access Your Applications
- App 1: http://app1.localhost
- App 2: http://app2.localhost
- App 3: http://app3.localhost
Summary
This setup effectively decouples the MySQL service into a separate container while allowing multiple Laravel applications to connect seamlessly. It simplifies database management and provides a scalable architecture where you can adjust each Laravel environment independently without affecting the shared database service. Let me know if you need further adjustments or assistance!
Leave a Comment