1
0
mirror of https://github.com/BookStackApp/BookStack.git synced 2025-10-20 20:12:39 +03:00

Dev: Played with an all-in-one docker environment

This commit is contained in:
Dan Brown
2025-10-06 13:06:12 +01:00
parent 146a6c01cc
commit 9d1c0e5dda
10 changed files with 161 additions and 87 deletions

View File

@@ -1,38 +1,48 @@
FROM php:8.3-apache
FROM ubuntu:24.04
# Install additional dependencies
RUN apt-get update && \
# Accept build arguments
ARG USER_ID=1000
ARG GROUP_ID=1000
ARG USERNAME=devuser
# Install dependencies and some build env tools
RUN export DEBIAN_FRONTEND=noninteractive && \
apt-get update && \
apt-get install -y \
git \
zip \
unzip \
libfreetype-dev \
libjpeg62-turbo-dev \
libldap2-dev \
libpng-dev \
libzip-dev \
wait-for-it && \
rm -rf /var/lib/apt/lists/*
bash git tmux vim nano htop curl supervisor unzip sudo \
mysql-server-8.0 apache2 php8.3 \
php8.3-fpm php8.3-curl php8.3-mbstring php8.3-ldap php8.3-xml php8.3-zip php8.3-gd php8.3-mysql php8.3-xdebug
# Install PHP extensions
RUN docker-php-ext-configure ldap --with-libdir="lib/$(gcc -dumpmachine)" && \
docker-php-ext-configure gd --with-freetype --with-jpeg && \
docker-php-ext-install -j$(nproc) pdo_mysql gd ldap zip && \
pecl install xdebug && \
docker-php-ext-enable xdebug
# Create group and user with specific IDs, and give user sudo access (for service management)
RUN userdel -r ubuntu && \
groupadd -g ${GROUP_ID} ${USERNAME} && \
useradd -u ${USER_ID} -g ${GROUP_ID} -m -s /bin/bash ${USERNAME} && \
echo "${USERNAME} ALL=(ALL) NOPASSWD:ALL" >> /etc/sudoers
# Install composer
RUN curl -sS https://getcomposer.org/installer | php -- --install-dir=/usr/local/bin --filename=composer
# Install build tools (composer/node/npm)
RUN curl -sS https://getcomposer.org/installer | php -- --install-dir=/usr/local/bin --filename=composer && \
mkdir -p "/home/${USERNAME}/.nvm" && export NVM_DIR="/home/${USERNAME}/.nvm" && curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.3/install.sh | bash && \
\. "/home/${USERNAME}/.nvm/nvm.sh" && \
nvm install 22 && \
chown -R ${USERNAME} "/home/${USERNAME}/.nvm" && \
echo 'export NVM_DIR="${HOME}/.nvm" && source "$NVM_DIR/nvm.sh"' >> "/home/${USERNAME}/.bashrc"
# Configure apache
RUN a2enmod rewrite && \
sed -ri -e 's!/var/www/html!${APACHE_DOCUMENT_ROOT}!g' /etc/apache2/sites-available/*.conf && \
sed -ri -e 's!/var/www/!${APACHE_DOCUMENT_ROOT}!g' /etc/apache2/apache2.conf /etc/apache2/conf-available/*.conf
# Configure apache, php & mysql
RUN a2dissite 000-default.conf && \
a2enmod rewrite proxy_fcgi setenvif && \
a2enconf php8.3-fpm && \
sed -i "s/www-data/${USERNAME}/g" "/etc/php/8.3/fpm/pool.d/www.conf" && \
sed -i "s/www-data/${USERNAME}/g" "/etc/apache2/envvars" && \
chmod 755 /var/run/mysqld
# Use the default production configuration and update it as required
RUN mv "$PHP_INI_DIR/php.ini-production" "$PHP_INI_DIR/php.ini" && \
sed -i 's/memory_limit = 128M/memory_limit = 512M/g' "$PHP_INI_DIR/php.ini"
ENV APACHE_DOCUMENT_ROOT="/app/public"
# Copy required configuration & entrypoint script
COPY supervisord.conf /etc/supervisor/conf.d/supervisord.conf
COPY apache.conf /etc/apache2/sites-enabled/bookstack.conf
COPY setup.sql /setup.sql
COPY entrypoint.sh /entrypoint.sh
# Set our user, working directory, entrypoint and default command
USER ${USERNAME}
WORKDIR /app
ENTRYPOINT ["/entrypoint.sh"]
CMD ["/bin/bash"]

34
dev/docker/apache.conf Normal file
View File

@@ -0,0 +1,34 @@
<VirtualHost *:80>
DocumentRoot /app/public/
<Directory /app/public/>
Options Indexes FollowSymLinks
AllowOverride None
Require all granted
<IfModule mod_rewrite.c>
<IfModule mod_negotiation.c>
Options -MultiViews -Indexes
</IfModule>
RewriteEngine On
# Handle Authorization Header
RewriteCond %{HTTP:Authorization} .
RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
# Redirect Trailing Slashes If Not A Folder...
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_URI} (.+)/$
RewriteRule ^ %1 [L,R=301]
# Handle Front Controller...
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ index.php [L]
</IfModule>
</Directory>
ErrorLog ${APACHE_LOG_DIR}/error.log
CustomLog ${APACHE_LOG_DIR}/access.log combined
</VirtualHost>

14
dev/docker/enter.sh Normal file
View File

@@ -0,0 +1,14 @@
#!/usr/bin/env bash
# Auto-detect your user ID
USER_ID=$(id -u)
GROUP_ID=$(id -g)
USERNAME=$(whoami)
# Export variables
export USER_ID
export GROUP_ID
export USERNAME
# Build & start the stack
docker-compose up -d --remove-orphans app && docker compose attach app

View File

@@ -1,15 +0,0 @@
#!/bin/bash
set -e
env
if [[ -n "$1" ]]; then
exec "$@"
else
composer install
wait-for-it db:3306 -t 45
php artisan migrate --database=mysql --force
chown -R www-data storage public/uploads bootstrap/cache
exec apache2-foreground
fi

View File

@@ -1,8 +0,0 @@
#!/bin/sh
set -e
npm install
npm rebuild node-sass
SHELL=/bin/sh exec npm run watch

23
dev/docker/entrypoint.sh Normal file
View File

@@ -0,0 +1,23 @@
#!/bin/bash
echo "Starting services..."
# Start supervisord in background
sudo /usr/bin/supervisord -sc /etc/supervisor/conf.d/supervisord.conf &
# Wait for MySQL to start
echo "Waiting for MySQL to be ready..."
for i in {1..30}; do
if sudo mysqladmin -u root ping &>/dev/null; then
break
fi
sleep 1
done
# Running MySQL startup script
echo "Setting up database..."
sudo mysql -u root < /setup.sql
# Execute whatever command was passed (default: /bin/bash)
echo "Setup done! Dropping you to shell-window or command ($@)"
exec "$@"

View File

@@ -1,5 +0,0 @@
# create test database
CREATE DATABASE IF NOT EXISTS `bookstack-test`;
# grant rights
GRANT ALL PRIVILEGES ON `bookstack-test`.* TO 'bookstack-test'@'%';

12
dev/docker/setup.sql Normal file
View File

@@ -0,0 +1,12 @@
-- Create databases
CREATE DATABASE IF NOT EXISTS `bookstack`;
CREATE DATABASE IF NOT EXISTS `bookstack-test`;
-- Create users
CREATE USER IF NOT EXISTS 'bookstack'@'%' IDENTIFIED BY 'bookstack';
CREATE USER IF NOT EXISTS 'bookstack-test'@'%' IDENTIFIED BY 'bookstack-test';
-- Grant rights
GRANT ALL PRIVILEGES ON `bookstack`.* to 'bookstack'@'%';
GRANT ALL PRIVILEGES ON `bookstack-test`.* TO 'bookstack-test'@'%';
FLUSH PRIVILEGES;

View File

@@ -0,0 +1,23 @@
[supervisord]
nodaemon=true
logfile=/var/log/supervisor/supervisord.log
pidfile=/var/run/supervisord.pid
[program:apache2]
command=/usr/sbin/apache2ctl -D FOREGROUND
autostart=true
autorestart=true
stdout_logfile=/var/log/supervisor/apache2.log
stderr_logfile=/var/log/supervisor/apache2.err
[program:php-fpm]
command=/usr/sbin/php-fpm8.3 -F
autostart=true
autorestart=true
stdout_logfile=/var/log/supervisor/php-fpm.log
[program:mysql]
command=/usr/sbin/mysqld --performance-schema=off
autostart=true
autorestart=true
stdout_logfile=/var/log/supervisor/mysql.log

View File

@@ -5,47 +5,33 @@ volumes:
db: {}
services:
db:
image: mysql:8.4
environment:
MYSQL_DATABASE: bookstack-dev
MYSQL_USER: bookstack-test
MYSQL_PASSWORD: bookstack-test
MYSQL_RANDOM_ROOT_PASSWORD: 'true'
volumes:
- ./dev/docker/init.db:/docker-entrypoint-initdb.d
- db:/var/lib/mysql
app:
build:
context: .
dockerfile: ./dev/docker/Dockerfile
context: ./dev/docker
args:
USER_ID: ${USER_ID:-1000}
GROUP_ID: ${GROUP_ID:-1000}
USERNAME: ${USERNAME:-devuser}
environment:
APP_URL: http://localhost:${DEV_PORT:-8080}
DB_CONNECTION: mysql
DB_HOST: db
DB_HOST: localhost
DB_PORT: 3306
DB_DATABASE: bookstack-dev
DB_USERNAME: bookstack-test
DB_PASSWORD: bookstack-test
TEST_DATABASE_URL: mysql://bookstack-test:bookstack-test@db/bookstack-test
DB_DATABASE: bookstack
DB_USERNAME: bookstack
DB_PASSWORD: bookstack
TEST_DATABASE_URL: mysql://bookstack-test:bookstack-test@localhost/bookstack-test
MAIL_DRIVER: smtp
MAIL_HOST: mailhog
MAIL_PORT: 1025
ports:
- ${DEV_PORT:-8080}:80
- ${DEV_DB_PORT:-33066}:3306
volumes:
- ./:/app
- ./dev/docker/php/conf.d/xdebug.ini:/usr/local/etc/php/conf.d/docker-php-ext-xdebug.ini
entrypoint: /app/dev/docker/entrypoint.app.sh
extra_hosts:
- "host.docker.internal:host-gateway"
node:
image: node:22-alpine
working_dir: /app
user: node
volumes:
- ./:/app
entrypoint: /app/dev/docker/entrypoint.node.sh
- ./:/app:z
- db:/var/lib/mysql
stdin_open: true
tty: true
mailhog:
image: mailhog/mailhog
ports: