Build a Complete Dockerized Laravel Environment with PHP, Nginx, MySQL, Redis and Mailpit

Setting up a Laravel development environment manually can take a significant amount of time. Installing PHP, Composer, Node.js, MySQL, Redis and a web server separately also becomes inconvenient when working on multiple projects.
That is why I created a Docker-based starter kit for Laravel projects.
The starter kit provides a complete development environment with:
- PHP 8.4-FPM
- Nginx 1.28.1
- MySQL 8.4
- Redis 7
- Node.js 22
- Composer 2
- Mailpit
- phpMyAdmin
- Laravel 13
---
Project Structure
The repository has the following structure:
laravel-docker-starterkit/
├── docker/
│ └── services/
│ ├── app/
│ │ ├── app.dockerfile
│ │ └── entrypoint.sh
│ └── web/
│ ├── web.dockerfile
│ └── vhost.conf
├── src/
│ ├── app/
│ ├── bootstrap/
│ ├── config/
│ ├── database/
│ ├── public/
│ ├── resources/
│ ├── routes/
│ ├── .env.example
│ ├── composer.json
│ └── package.json
├── docker-compose.yml
└── local.shThe src directory contains the Laravel application.
The docker directory contains the Docker configuration for the application and web server.
---
Docker Architecture
The starter kit uses separate containers for the main application layers:
Browser
│
▼
┌─────────────┐
│ Nginx │
│ :8000 │
└──────┬──────┘
│
│ FastCGI
▼
┌─────────────┐
│ PHP-FPM 8.4 │
│ app │
└──────┬──────┘
│
┌────────────┼────────────┐
▼ ▼ ▼
MySQL Redis MailpitNginx receives HTTP requests and forwards PHP requests to the PHP-FPM container through app:9000.
The Laravel application communicates with MySQL, Redis and Mailpit through the Docker network.
---
PHP Application Container
The application container is based on:
php:8.4-fpm-bookwormIt contains the PHP extensions required by the application, including:
bcmathgdintlmbstringopcachepcntlpdo_mysqlzip- Redis
- Composer 2
- Node.js 22
- npm
The container working directory is:
/var/wwwand the local:
./srcdirectory is mounted there.
---
Nginx
Nginx 1.28.1 is used as the web server.
The Laravel public directory is configured as the web root:
/var/www/publicPHP requests are forwarded to PHP-FPM:
fastcgi_pass app:9000;Here, app is the Docker Compose service name.
The default host port is:
8000Therefore, the application is available at:
http://localhost:8000---
MySQL
MySQL 8.4 is used as the database server.
The Docker Compose service is named:
databaseInside the Docker network, Laravel connects to MySQL using the service name rather than localhost:
DB_CONNECTION=mysql
DB_HOST=database
DB_PORT=3306
DB_DATABASE=laravel
DB_USERNAME=laravel
DB_PASSWORD=secretMySQL data is stored in a Docker named volume, so recreating containers does not automatically remove the database data.
---
Redis
Redis 7 is used for caching and other Laravel-related workloads.
The Laravel configuration can point to the Redis service using:
REDIS_HOST=redis
REDIS_PORT=6379Redis also uses a persistent Docker volume.
This allows the application to use Redis for cache, sessions, queues or other supported Laravel features.
---
Mailpit
Mailpit is included for local email development.
Instead of sending emails to real recipients, Laravel sends them to Mailpit where they can be inspected through a browser.
Laravel configuration:
MAIL_MAILER=smtp
MAIL_HOST=mailpit
MAIL_PORT=1025The Mailpit web interface is available at:
http://localhost:8025and the SMTP server listens on:
localhost:1025This is especially useful for testing registration emails, password resets and notifications during development.
---
phpMyAdmin
An optional phpMyAdmin service is also included for database management.
It is available through the Docker Compose tools profile.
Default URL:
http://localhost:8888This provides a convenient browser-based interface for managing the MySQL database.
The main Laravel environment does not depend on phpMyAdmin, so it can be omitted when it is not needed.
---
Environment Configuration
First create the Laravel environment file:
cp src/.env.example src/.envThen configure Laravel to communicate with the Docker services:
APP_URL=http://localhost:8000
DB_CONNECTION=mysql
DB_HOST=database
DB_PORT=3306
DB_DATABASE=laravel
DB_USERNAME=laravel
DB_PASSWORD=secret
REDIS_HOST=redis
REDIS_PORT=6379
MAIL_MAILER=smtp
MAIL_HOST=mailpit
MAIL_PORT=1025One important detail is that localhost should not be used as the database host from inside the Laravel container.
Docker services communicate using their Compose service names:
database
redis
mailpit---
First Boot
Clone the repository:
git clone https://github.com/mirrrjr/laravel-docker-starterkit.git
cd laravel-docker-starterkitCreate the environment file:
cp src/.env.example src/.envThen run:
./local.sh initThe init command:
- Builds the Docker images.
- Starts the containers.
- Installs Composer dependencies.
- Generates the Laravel application key.
- Runs the database migrations.
- Installs npm dependencies.
Once everything is ready, open:
http://localhost:8000---
The local.sh Helper
The repository includes local.sh as a helper for common Docker and Laravel commands.
Start the environment:
./local.sh upStop and remove containers:
./local.sh downRestart the environment:
./local.sh restartRebuild the Docker environment:
./local.sh rebuildView logs:
./local.sh logsView logs for a specific service:
./local.sh logs appEnter the application container:
./local.sh shellRun an Artisan command:
./local.sh artisan migrateRun Composer:
./local.sh composer installRun npm:
./local.sh npm installThe main purpose of this helper is to avoid repeatedly typing long docker compose exec commands.
---
Frontend Development
The application container includes Node.js 22 and npm.
Install dependencies:
./local.sh npm installStart the Vite development server:
./local.sh npm run devBuild frontend assets:
./local.sh npm run buildLaravel frontend assets are managed through Vite.
---
Working with the Database
Run migrations:
./local.sh artisan migrateReset the database:
./local.sh artisan migrate:freshReset and seed:
./local.sh artisan migrate:fresh --seedOpen Laravel Tinker:
./local.sh artisan tinkerAll of these commands can be executed without installing PHP directly on the host system.
---
Docker Service Ports
The default ports are:
| Service | Host port | Container port |
|---|---|---|
| --------------- | --------: | -------------: |
| Laravel / Nginx | 8000 | 80 |
| MySQL | 3306 | 3306 |
| Redis | 6379 | 6379 |
| Mailpit SMTP | 1025 | 1025 |
| Mailpit Web | 8025 | 8025 |
| phpMyAdmin | 8888 | 80 |
For example:
APP_PORT=8080would make the application available at:
http://localhost:8080---
Why Docker?
The main advantage of this setup is that the development environment is isolated from the host operating system.
You do not need to install and configure:
PHP
MySQL
Redis
Node.js
Composer
Nginxseparately for every project.
Docker keeps the required environment together with the project.
Another developer can clone the repository and use the same PHP, Node.js, MySQL and Redis setup.
This helps to:
- reduce environment inconsistencies;
- simplify dependency management;
- shorten project setup time;
- make onboarding easier;
- keep development environments reproducible.
Conclusion
The Laravel Docker Starter Kit provides a ready-to-use development environment for Laravel applications.
The main stack is:
Laravel
│
├── PHP 8.4-FPM
├── Nginx 1.28
├── MySQL 8.4
├── Redis 7
├── Node.js 22
├── Mailpit
└── phpMyAdminThe goal is simple: start Laravel development without spending time manually configuring the entire local environment.
Clone the repository, configure .env, and run:
./local.sh initYour Dockerized Laravel development environment is then ready to use.