Skip to content

Laradock #1216

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
May 18, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
[submodule "laradock"]
path = laradock
url = https://github.com/Laradock/laradock.git
143 changes: 90 additions & 53 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -1,60 +1,97 @@
# Stage 1: Compile Frontend Assets
FROM node:20-alpine AS node_builder

WORKDIR /app/frontend

# Copy package files and essential build configuration
COPY package.json package-lock.json* webpack.mix.js tailwind.config.js postcss.config.js* .babelrc* ./
# Ensure postcss.config.js and .babelrc are optional by using * in case they don't exist

# Install all dependencies (including devDependencies like laravel-mix)
RUN npm ci

# Copy frontend source code (js, css, images, etc.)
COPY resources/js ./resources/js
COPY resources/css ./resources/css
COPY resources/img ./resources/img
# Add other relevant resource directories if needed

# Compile assets for production
RUN npm run production

# Stage 2: Setup PHP Application Environment using richarvey/nginx-php-fpm
FROM richarvey/nginx-php-fpm:3.1.6 AS app

# Set Laravel Environment Variables as per the article
ENV APP_ENV production
ENV APP_DEBUG false
ENV LOG_CHANNEL stderr
ENV APP_KEY ${APP_KEY}
ENV SKIP_COMPOSER 1
ENV WEBROOT /var/www/html/public
ENV PHP_ERRORS_STDERR 1 # Send PHP errors to stderr for Docker logging
ENV RUN_SCRIPTS 1 # Enable execution of scripts in /scripts directory
ENV REAL_IP_HEADER 1 # If behind a proxy, trust X-Forwarded-For
ENV COMPOSER_ALLOW_SUPERUSER 1 # Allow composer to run as root if needed by scripts

# Set working directory
# Stage 1: Base with PHP, Composer, and common extensions
# We'll use an official PHP image as a base for PHP-FPM
FROM php:8.2-fpm-alpine AS php_base

# Install system dependencies for PHP extensions and other tools
RUN apk add --no-cache \
bash \
curl \
git \
supervisor \
nginx \
# For common PHP extensions
libzip-dev \
libpng-dev \
libjpeg-turbo-dev \
freetype-dev \
icu-dev \
libxml2-dev \
# For pdo_mysql
mysql-client

# Install PHP extensions
# You can customize this list based on Laradock's PHP-FPM Dockerfile or your app's needs
RUN docker-php-ext-configure gd --with-freetype --with-jpeg \
&& docker-php-ext-install -j$(nproc) \
gd \
intl \
opcache \
pdo_mysql \
zip \
xml \
bcmath \
pcntl \
exif \
sockets

# Get latest Composer
COPY --from=composer:latest /usr/bin/composer /usr/bin/composer

# Set working directory for the application
WORKDIR /var/www/html

# Copy all application files
# Copy application code
COPY . .

# Copy compiled assets from the node_builder stage
COPY --from=node_builder /app/frontend/public ./public
# Install Composer dependencies
RUN composer install --no-dev --no-interaction --no-progress --optimize-autoloader

# Optimize Laravel (optional here, can also be done at runtime start, but better in image)
RUN php artisan config:cache
RUN php artisan route:cache
# RUN php artisan view:cache # view:cache can sometimes be problematic if paths change

# Fix permissions for storage and bootstrap cache
RUN chown -R www-data:www-data storage bootstrap/cache public \
&& chmod -R 775 storage bootstrap/cache public

# Stage 2: Final image with Nginx and Supervisor
FROM alpine:latest

# Copy our Nginx site configuration to the standard location for richarvey images
COPY nginx-site.conf /etc/nginx/sites-available/default
# Copy PHP-FPM and application from the php_base stage
COPY --from=php_base /usr/local/etc/php-fpm.d/ /usr/local/etc/php-fpm.d/
COPY --from=php_base /usr/local/etc/php/ /usr/local/etc/php/
COPY --from=php_base /usr/local/sbin/php-fpm /usr/local/sbin/php-fpm
COPY --from=php_base /usr/local/bin/php /usr/local/bin/php
COPY --from=php_base /usr/bin/composer /usr/bin/composer
COPY --from=php_base /var/www/html /var/www/html
COPY --from=php_base /etc/ssl/certs/ca-certificates.crt /etc/ssl/certs/

# Install Nginx and Supervisor from Alpine packages (if not already in php_base or if we want a clean stage)
RUN apk add --no-cache nginx supervisor mysql-client bash

# Create Nginx log directory if it doesn't exist from package install
RUN mkdir -p /var/log/nginx && \
chown -R nginx:nginx /var/log/nginx && \
mkdir -p /var/lib/nginx && \
chown -R nginx:nginx /var/lib/nginx && \
# Create run directory for php-fpm and nginx pid
mkdir -p /run/php && \
mkdir -p /run/nginx

# Copy Nginx configuration
# We will create these files next: nginx.conf and supervisord.conf
COPY nginx-prod.conf /etc/nginx/nginx.conf
COPY laravel-site.conf /etc/nginx/http.d/default.conf

# Copy Supervisor configuration
COPY supervisord.conf /etc/supervisord.conf

# Application root
WORKDIR /var/www/html

# Copy our deploy script to the location where richarvey image expects to run scripts
# Ensure deploy.sh has necessary commands (composer install, migrations, cache)
RUN mkdir -p /scripts
COPY deploy.sh /scripts/00-laravel-deploy.sh
# Install dos2unix, convert line endings, and ensure the script is executable
RUN apk add --no-cache dos2unix && \
dos2unix /scripts/00-laravel-deploy.sh && \
chmod +x /scripts/00-laravel-deploy.sh
# Expose port 80 for Nginx
EXPOSE 80

# The base image (richarvey/nginx-php-fpm) handles starting Nginx, PHP-FPM,
# and running scripts from /scripts. Its default CMD is /start.sh.
CMD ["/start.sh"]
# Start Supervisor
CMD ["/usr/bin/supervisord", "-c", "/etc/supervisord.conf"]
57 changes: 57 additions & 0 deletions docker-compose.render.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
version: '3.8'

services:
php-fpm:
build:
context: . # We'll build from the project root
dockerfile: php-fpm.render.dockerfile # A dedicated Dockerfile for this service
args:
# Example: Use PHP_VERSION from Laradock's .env or set a default
# This can be overridden by Render environment variables if needed
LARADOCK_PHP_VERSION: ${PHP_VERSION:-8.2} # Defaulting to 8.2 as in previous Dockerfile
volumes:
# Mount Render's persistent disk for Laravel storage
# The name 'laravel-storage' should match the disk name in render.yaml
- laravel-storage:/var/www/html/storage
# Environment variables will be injected by Render from render.yaml
# working_dir is typically /var/www/html (set in php-fpm.render.dockerfile)

nginx:
build:
context: ./laradock/nginx # Use Laradock's Nginx Dockerfile
args:
# Environment variables from Laradock's .env can be passed as build args if needed
# For example, if Laradock's Nginx Dockerfile uses them.
# Common ones are already handled by Laradock's Nginx entrypoint/config.
PHP_UPSTREAM_CONTAINER: php-fpm # Ensure it points to our php-fpm service
PHP_UPSTREAM_PORT: 9000
NGINX_HOST_LOG_PATH: /var/log/nginx # Standard log path
# Ensure NGINX_SITES_PATH points where Laradock's Dockerfile expects to find site configs
# NGINX_SITES_PATH: /etc/nginx/sites-available # Default in Laradock .env
volumes:
# The application code (especially /public) needs to be accessible by Nginx.
# Our php-fpm service builds the code into /var/www/html.
# We need to share this with Nginx.
# The 'app_code' volume is defined below and should be populated by the php-fpm service.
# However, for Render, it's often better if the Nginx image also has the static assets.
# Laradock's Nginx Dockerfile usually copies from APP_CODE_PATH_HOST.
# Let's ensure our php-fpm service populates the app_code volume,
# and nginx mounts it.
# Alternatively, nginx Dockerfile could also COPY ../public /var/www/html/public
- app_code:/var/www/html
ports:
- "80:80"
depends_on:
- php-fpm
# Environment variables from render.yaml will be available.
# Laradock's Nginx often uses NGINX_APP_CODE_PATH_CONTAINER=/var/www/html
# and expects the site config to set root to $NGINX_APP_CODE_PATH_CONTAINER/public
environment:
NGINX_APP_CODE_PATH_CONTAINER: /var/www/html # To align with Laradock's Nginx config expectations
# Other NGINX_... variables from laradock/.env can be set here if needed by the entrypoint

volumes:
laravel-storage: # This name must match the disk name in render.yaml
driver: local # For local testing; Render handles this differently
app_code: # Volume to share application code if needed, populated by php-fpm build
driver: local
1 change: 1 addition & 0 deletions laradock
Submodule laradock added at f2b595
27 changes: 27 additions & 0 deletions nginx.render.dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
# nginx.render.dockerfile
# Use Laradock's Nginx image as a base
FROM laradock/nginx:latest

# Application code is expected to be in /var/www/html
# Nginx needs access to the public directory.
# We'll copy the application's public directory.
# Note: The php-fpm container builds the full app. For Nginx, we primarily need static assets.
# If your app has a build step for frontend assets that places them in public/,
# ensure that step is run before this Dockerfile builds or that the assets are copied.
# The php-fpm.render.dockerfile already copies the whole app, so assets should be there.

WORKDIR /var/www/html

# Copy only the public directory from the application source for Nginx to serve static files.
# The rest of the app (PHP files) will be handled by PHP-FPM.
# This assumes the build context for docker-compose is the project root.
COPY public ./public

# Copy custom Nginx site configuration for the Laravel application
# We will create 'laravel.render.conf' next.
COPY laravel.render.conf /etc/nginx/sites-available/default.conf

# Expose port 80 (already exposed by base image, but good for clarity)
EXPOSE 80

# CMD is inherited from laradock/nginx, which starts nginx.
34 changes: 34 additions & 0 deletions php-fpm.render.dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
# php-fpm.render.dockerfile
ARG LARADOCK_PHP_VERSION=8.2
FROM laradock/php-fpm:${LARADOCK_PHP_VERSION}

# Set working directory
WORKDIR /var/www/html

# Install pdo_mysql if not present by default in this specific Laradock base
# (Laradock's build process for php-fpm usually includes common extensions based on its .env)
# For a production image, ensure all necessary extensions are explicitly built or verified.
# Example: RUN docker-php-ext-install pdo_mysql zip bcmath pcntl exif sockets ...

# Copy application code from the build context (project root)
COPY . .

# Install Composer dependencies
# Composer should be available in the laradock/php-fpm base image.
RUN composer install --no-dev --no-interaction --no-progress --optimize-autoloader

# Run Laravel optimizations
RUN php artisan config:cache && \
php artisan route:cache && \
php artisan view:cache

# Ensure storage, bootstrap/cache, and public directories are writable by www-data
# Adjust ownership/permissions as necessary for your application's needs.
# The user for php-fpm is typically www-data.
RUN chown -R www-data:www-data storage bootstrap/cache public && \
chmod -R 775 storage bootstrap/cache public

# Expose port 9000 for PHP-FPM (already exposed by base image, but good for clarity)
EXPOSE 9000

# The CMD is inherited from laradock/php-fpm, which starts php-fpm.
Loading