From 2c1a562bf2919ce6d27bca52f3824942613f9ea1 Mon Sep 17 00:00:00 2001 From: Jonatan Rek Date: Sun, 23 Nov 2025 22:34:17 +0100 Subject: [PATCH] Initial Works --- Dockerfile | 130 ++++++++++++++++++++++++++ start.sh | 91 ++++++++++++++++++ supervisor/conf.d/laravel-queues.conf | 38 ++++++++ supervisor/supervisord.conf | 18 ++++ 4 files changed, 277 insertions(+) create mode 100644 Dockerfile create mode 100644 start.sh create mode 100644 supervisor/conf.d/laravel-queues.conf create mode 100644 supervisor/supervisord.conf diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..4668962 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,130 @@ +# Use PHP with Apache as the base image +FROM php:8.4-apache + +# Timezone +ENV TZ="Europe/Prague" +RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone +RUN printf '[Date]\ndate.timezone="%s"\n', $TZ > /usr/local/etc/php/conf.d/tzone.ini + +# OPcache +ENV PHP_OPCACHE_VALIDATE_TIMESTAMPS="1" \ + PHP_OPCACHE_MAX_ACCELERATED_FILES="10000" \ + PHP_OPCACHE_MEMORY_CONSUMPTION="192" \ + PHP_OPCACHE_MAX_WASTED_PERCENTAGE="10" + +# PHP +RUN export PHP_INI_DIR="$PHP_INI_DIR/php.ini" +RUN mv "$PHP_INI_DIR/php.ini-production" "$PHP_INI_DIR/php.ini" && \ + sed -i "s|memory_limit = 128M|memory_limit = 256M |g" "$PHP_INI_DIR/php.ini" && \ + sed -i "s|upload_max_filesize = 2M|upload_max_filesize = 100M |g" "$PHP_INI_DIR/php.ini" && \ + sed -i "s|post_max_size = 8M|post_max_size = 100M |g" "$PHP_INI_DIR/php.ini" + +# Install Additional System Dependencies +RUN rm -f /etc/apt/apt.conf.d/docker-clean +RUN --mount=type=cache,target=/var/cache/apt \ + apt-get update && apt-get install -yqq --no-install-recommends \ + git \ + libpq-dev \ + libzip-dev \ + zip \ + nodejs \ + npm \ + cron \ + nano \ + default-mysql-client \ + postgresql-client \ + imagemagick \ + libmagickwand-dev \ + supervisor && \ + git clone https://github.com/Imagick/imagick --depth 1 /tmp/imagick && \ + cd /tmp/imagick && \ + phpize && \ + ./configure && \ + make && \ + make install && \ + apt-get autoremove && \ + apt-get clean && \ + rm -rf /var/lib/apt/lists/* && \ + npm config set cache /tmp --global && \ + mkdir -p /var/log/supervisor + +# Enable Apache mod_rewrite for URL rewriting +RUN a2enmod rewrite + +# Install PHP extensions +RUN docker-php-ext-install pdo_mysql pgsql pdo_pgsql zip opcache pcntl sockets +RUN docker-php-ext-enable imagick + +#OPCACHE +RUN echo '[opcache]\n\ +opcache.enable=1\n\ +opcache.revalidate_freq=0\n\ +opcache.validate_timestamps=${PHP_OPCACHE_VALIDATE_TIMESTAMPS}\n\ +opcache.max_accelerated_files=${PHP_OPCACHE_MAX_ACCELERATED_FILES}\n\ +opcache.memory_consumption=${PHP_OPCACHE_MEMORY_CONSUMPTION}\n\ +opcache.max_wasted_percentage=${PHP_OPCACHE_MAX_WASTED_PERCENTAGE}\n\ +opcache.interned_strings_buffer=16\n\ +opcache.fast_shutdown=1' >> "$PHP_INI_DIR/conf.d/opcache.ini" + +#SUPERVISORD +COPY supervisor/* /etc/supervisor + +# Configure Apache DocumentRoot to point to Laravel's public directory +# and update Apache configuration files +ENV APACHE_DOCUMENT_ROOT=/var/www/html/public +RUN 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 + +# Setup Crone +RUN mkdir -p /var/log/cron && \ + echo "* * * * * www-data cd /var/www/html && /usr/local/bin/php artisan schedule:run >> /dev/null 2>&1" >> /etc/crontab && \ + echo "* * * * * www-data cd /var/www/html && /usr/local/bin/php artisan queue:work --queue=default,importstatistics --stop-when-empty >> /dev/null 2>&1" >> /etc/crontab && \ + echo "* * * * * www-data cd /var/www/html && /usr/local/bin/php artisan queue:work --queue=statistics --stop-when-empty >> /dev/null 2>&1" >> /etc/crontab && \ + echo "* * * * * www-data cd /var/www/html && /usr/local/bin/php artisan queue:work --queue=detections --stop-when-empty >> /dev/null 2>&1" >> /etc/crontab + +# Install composer # bun +ENV COMPOSER_ALLOW_SUPERUSER=1 +RUN curl -sS https://getcomposer.org/installer | php -- --install-dir=/usr/local/bin --filename=composer +RUN chown -R www-data:www-data /var/www/html && \ + chmod -R 775 /var/www/html + +# Patch Docker Entrypoint +RUN sed -i 's/^exec /printenv > \/etc\/environment\n\nexec /' /usr/local/bin/apache2-foreground && \ + sed -i 's/^exec /service cron start\n\nexec /' /usr/local/bin/apache2-foreground + +# Install project composer dependencies +USER www-data +COPY --chown=www-data:www-data composer.* /var/www/html +RUN --mount=type=cache,target=/root/.composer/vendor \ + composer install --prefer-dist --no-dev -o --no-scripts + +# Install project npm dependencies +COPY --chown=www-data:www-data package*.json /var/www/html +RUN npm install + +# Copy the application code +COPY --chown=www-data:www-data . /var/www/html +RUN --mount=type=cache,target=/root/.composer/vendor \ + composer install --prefer-dist --no-dev -o +RUN npm run build +USER root + +# Fix Permissions +RUN chown -R www-data:www-data /var/www/html && \ + find /var/www/html -type d ! -perm 775 -print0 | xargs -0 -r -n 100 -P 10000 chmod 775 && \ + find /var/www/html -type f -not -name "*.sh" ! -perm 664 -print0 | xargs -0 -r -n 100 -P 10000 chmod 664 + +#Start Container +RUN chmod +x /var/www/html/start.sh +CMD ["/var/www/html/start.sh"] + +# Set the working directory +VOLUME /var/www/html/storage/app + +RUN mkdir -p /config +VOLUME /config + +EXPOSE 8899 + +# Start Apache +WORKDIR /var/www/html/ diff --git a/start.sh b/start.sh new file mode 100644 index 0000000..1bf533e --- /dev/null +++ b/start.sh @@ -0,0 +1,91 @@ +#!/bin/bash +set -e + +# ----- LOGGING FUNCTIONS ----- +log_info() { echo -e "\033[1;34m[INFO]\033[0m $1"; } +log_warn() { echo -e "\033[1;33m[WARN]\033[0m $1"; } +log_error() { echo -e "\033[1;31m[ERROR]\033[0m $1"; } + +# ----- START ----- +log_info "Starting Laravel container setup" + +init=false + +# Initialize environment +if [ ! -f /config/.env ]; then + log_info "Creating .env from example" + cp .env.example .env + # Ensure APP_KEY exists + if ! grep -q "^APP_KEY=base64" .env; then + log_info "Generating application key" + php artisan key:generate + fi + cp .env /config/.env + init=true +else + log_info "Using existing /config/.env" + cp /config/.env .env +fi + +# SQLite database initialization +if { grep -iq "^DB_CONNECTION=sqlite" .env && [ "$DB_CONNECTION" = "sqlite" ]; } || [ "$DEPLOY_ENV" = "sqlite" ]; then + if [ ! -f database/database.sqlite ]; then + log_info "Creating empty SQLite database" + touch database/database.sqlite + init=true + fi +fi + +# Composer dependencies +if [ "$init" = "true" ] || [ "$(echo "$APP_DEBUG" | tr '[:upper:]' '[:lower:]')" = "true" ]; then + log_info "Initial setup nebo debug mód - instalace Composeru s dev závislostmi" + composer install --prefer-dist --optimize-autoloader +else + log_info "Produkční instalace - Composer bez dev závislostí" + composer install --prefer-dist --no-dev --optimize-autoloader +fi + +# Check Laravel module dependencies +log_info "Checking Laravel module dependencies..." +if php artisan app:check-module-dependencies; then + log_info "All module dependencies satisfied" +else + log_error "Missing module dependencies - exiting" + if [ "$init" != "true" ] && [ "$(echo "$APP_DEBUG" | tr '[:upper:]' '[:lower:]')" != "true" ]; then + exit 1 + fi +fi + +# Link storage and seed database if first init +if [ "$init" = true ]; then + log_info "Linking storage directory" + php artisan storage:link +fi + +# Migrate database +log_info "Running database migrations" +php artisan migrate --force --no-interaction + +# Clear Laravel caches +log_info "Clearing Laravel caches" +php artisan cache:clear +php artisan config:clear +php artisan route:clear +php artisan view:clear + +if [ "$(echo "$APP_DEBUG" | tr '[:upper:]' '[:lower:]')" = "false" ]; then + php artisan config:cache + php artisan route:cache + php artisan view:cache + sed -ri -e 's!opcache.enable=1!opcache.enable=0!g' "${PHP_INI_DIR}/conf.d/opcache.ini" +fi + +#supervisord +/usr/bin/supervisord -n -c /etc/supervisor/supervisord.conf + +#Start Socket Server +php artisan reverb:start --host=0.0.0.0 --port=8899 --no-interaction --debug & + +# Start Apache +log_info "Starting Apache server" +exec apache2-foreground diff --git a/supervisor/conf.d/laravel-queues.conf b/supervisor/conf.d/laravel-queues.conf new file mode 100644 index 0000000..3726f47 --- /dev/null +++ b/supervisor/conf.d/laravel-queues.conf @@ -0,0 +1,38 @@ +[program:laravel-worker-default] +process_name=%(program_name)s_%(process_num)02d +command=php /var/www/html/artisan queue:work --queue=default,importstatistics +autostart=true +autorestart=true +stopasgroup=true +killasgroup=true +numprocs=1 +redirect_stderr=true +stdout_logfile=/var/www/html/storage/logs/worker.log +stopwaitsecs=3600 +stdout_logfile_maxbytes=5MB + +[program:laravel-worker-statistics] +process_name=%(program_name)s_%(process_num)02d +command=php /var/www/html/artisan queue:work --queue=statisticss +autostart=true +autorestart=true +stopasgroup=true +killasgroup=true +numprocs=1 +redirect_stderr=true +stdout_logfile=/var/www/html/storage/logs/worker.log +stopwaitsecs=3600 +stdout_logfile_maxbytes=5MB + +[program:laravel-worker-detections] +process_name=%(program_name)s_%(process_num)02d +command=php /var/www/html/artisan queue:work --queue=detectionss +autostart=true +autorestart=true +stopasgroup=true +killasgroup=true +numprocs=1 +redirect_stderr=true +stdout_logfile=/var/www/html/storage/logs/worker.log +stopwaitsecs=3600 +stdout_logfile_maxbytes=5MB \ No newline at end of file diff --git a/supervisor/supervisord.conf b/supervisor/supervisord.conf new file mode 100644 index 0000000..80b5f35 --- /dev/null +++ b/supervisor/supervisord.conf @@ -0,0 +1,18 @@ +[supervisord] +logfile=/etc/supervisor/logs/supervisord.log ; main log file; default $CWD/supervisord.log +logfile_maxbytes=5MB ; max main logfile bytes b4 rotation; default 50MB +logfile_backups=10 ; # of main logfile backups; 0 means none, default 10 +loglevel=info ; log level; default info; others: debug,warn,trace +pidfile=/tmp/supervisord.pid ; supervisord pidfile; default supervisord.pid +nodaemon=false ; start in foreground if true; default false +minfds=1024 ; min. avail startup file descriptors; default 1024 +minprocs=200 ; min. avail process descriptors;default 200 + +[rpcinterface:supervisor] +supervisor.rpcinterface_factory = supervisor.rpcinterface:make_main_rpcinterface + +[supervisorctl] +serverurl=unix:///tmp/supervisor.sock ; use a unix:// URL for a unix socket + +[include] +files = /etc/supervisor/conf.d/*.conf \ No newline at end of file