++ Primo Caricamento
This commit is contained in:
60
docker/nginx/default.conf
Normal file
60
docker/nginx/default.conf
Normal file
@@ -0,0 +1,60 @@
|
||||
server {
|
||||
listen 80;
|
||||
server_name localhost;
|
||||
|
||||
# La root punta a public/ di Laravel, NON alla root del progetto.
|
||||
# Motivo: public/ è l'unica cartella esposta al web.
|
||||
# Il resto del codice (app/, config/, .env…) è fuori dalla webroot = sicuro.
|
||||
root /var/www/public;
|
||||
index index.php index.html;
|
||||
|
||||
# Charset e log
|
||||
charset utf-8;
|
||||
access_log /var/log/nginx/portale_access.log;
|
||||
error_log /var/log/nginx/portale_error.log;
|
||||
|
||||
# Dimensione massima upload (per allegati cliente, loghi, ecc.)
|
||||
client_max_body_size 50M;
|
||||
|
||||
# ─────────────────────────────────────────────────────────────
|
||||
# Regola principale: "try_files"
|
||||
# Per ogni richiesta, Nginx prova nell'ordine:
|
||||
# 1. $uri → cerca il file esatto (es. /css/app.css)
|
||||
# 2. $uri/ → cerca come directory
|
||||
# 3. /index.php?$query_string → passa tutto a Laravel (front controller)
|
||||
# ─────────────────────────────────────────────────────────────
|
||||
location / {
|
||||
try_files $uri $uri/ /index.php?$query_string;
|
||||
}
|
||||
|
||||
# ─────────────────────────────────────────────────────────────
|
||||
# Gestione file PHP: passa le richieste a PHP-FPM
|
||||
# "app:9000" → nome del container PHP nel docker-compose + porta FPM
|
||||
# ─────────────────────────────────────────────────────────────
|
||||
location ~ \.php$ {
|
||||
fastcgi_pass app:9000;
|
||||
fastcgi_index index.php;
|
||||
|
||||
# SCRIPT_FILENAME: percorso assoluto del file PHP da eseguire
|
||||
fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
|
||||
include fastcgi_params;
|
||||
|
||||
# Timeout generosi per operazioni lunghe (import, report, ecc.)
|
||||
fastcgi_read_timeout 300;
|
||||
}
|
||||
|
||||
# ─────────────────────────────────────────────────────────────
|
||||
# Blocca accesso ai file nascosti (es. .env, .git, .htaccess)
|
||||
# IMPORTANTE: non esporre mai il .env al web!
|
||||
# ─────────────────────────────────────────────────────────────
|
||||
location ~ /\.(?!well-known).* {
|
||||
deny all;
|
||||
}
|
||||
|
||||
# Cache browser per asset statici (performance)
|
||||
location ~* \.(css|js|jpg|jpeg|png|gif|ico|svg|woff|woff2|ttf|eot)$ {
|
||||
expires 1y;
|
||||
add_header Cache-Control "public, immutable";
|
||||
access_log off;
|
||||
}
|
||||
}
|
||||
93
docker/php/Dockerfile
Normal file
93
docker/php/Dockerfile
Normal file
@@ -0,0 +1,93 @@
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
# Immagine base: PHP 8.2 in modalità FPM (FastCGI Process Manager)
|
||||
# FPM è la modalità usata in produzione con Nginx.
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
FROM php:8.2-fpm
|
||||
|
||||
# Argomenti di build (puoi sovrascriverli con --build-arg)
|
||||
ARG USER_ID=1000
|
||||
ARG GROUP_ID=1000
|
||||
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
# 1. Dipendenze di sistema e estensioni PHP necessarie a Laravel
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
RUN apt-get update && apt-get install -y \
|
||||
# Strumenti base
|
||||
git \
|
||||
curl \
|
||||
unzip \
|
||||
zip \
|
||||
# Librerie per le estensioni PHP
|
||||
libpng-dev \
|
||||
libonig-dev \
|
||||
libxml2-dev \
|
||||
libzip-dev \
|
||||
libpq-dev \
|
||||
libredis-dev \
|
||||
# Per generazione immagini/PDF (opzionale ma comune)
|
||||
libfreetype6-dev \
|
||||
libjpeg62-turbo-dev \
|
||||
# Pulizia cache apt per ridurre dimensione immagine
|
||||
&& apt-get clean \
|
||||
&& rm -rf /var/lib/apt/lists/*
|
||||
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
# 2. Estensioni PHP
|
||||
# docker-php-ext-install → estensioni native PHP
|
||||
# pecl install → estensioni da PECL (es. Redis)
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
RUN docker-php-ext-configure gd --with-freetype --with-jpeg \
|
||||
&& docker-php-ext-install \
|
||||
pdo_mysql \
|
||||
mbstring \
|
||||
exif \
|
||||
pcntl \
|
||||
bcmath \
|
||||
gd \
|
||||
zip \
|
||||
xml \
|
||||
opcache
|
||||
|
||||
# Estensione Redis via PECL
|
||||
RUN pecl install redis \
|
||||
&& docker-php-ext-enable redis
|
||||
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
# 3. Composer: gestore dipendenze PHP
|
||||
# Lo copiamo dall'immagine ufficiale di Composer (multi-stage)
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
COPY --from=composer:2.7 /usr/bin/composer /usr/bin/composer
|
||||
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
# 4. Utente non-root per sicurezza
|
||||
# Usiamo lo stesso UID/GID del tuo utente host per evitare
|
||||
# problemi di permessi sui file montati con volume.
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
RUN groupmod -o -g ${GROUP_ID} www-data \
|
||||
&& usermod -o -u ${USER_ID} -g www-data www-data
|
||||
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
# 5. Directory di lavoro e permessi
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
WORKDIR /var/www
|
||||
|
||||
RUN mkdir -p \
|
||||
storage/app/public \
|
||||
storage/framework/cache/data \
|
||||
storage/framework/sessions \
|
||||
storage/framework/testing \
|
||||
storage/framework/views \
|
||||
storage/logs \
|
||||
bootstrap/cache \
|
||||
&& chown -R www-data:www-data /var/www
|
||||
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
# 6. Script di avvio
|
||||
# ────────────────────────────────────────────────────────────────
|
||||
COPY docker/php/entrypoint.sh /usr/local/bin/entrypoint.sh
|
||||
RUN chmod +x /usr/local/bin/entrypoint.sh
|
||||
|
||||
USER www-data
|
||||
|
||||
ENTRYPOINT ["/usr/local/bin/entrypoint.sh"]
|
||||
CMD ["php-fpm"]
|
||||
112
docker/php/entrypoint.sh
Normal file
112
docker/php/entrypoint.sh
Normal file
@@ -0,0 +1,112 @@
|
||||
#!/bin/bash
|
||||
# ─────────────────────────────────────────────────────────────────────────────
|
||||
# Entrypoint: eseguito ad ogni avvio del container.
|
||||
# Si occupa di preparare l'applicazione la prima volta e ad ogni restart.
|
||||
# ─────────────────────────────────────────────────────────────────────────────
|
||||
set -e # Interrompi se un comando fallisce
|
||||
|
||||
echo "────────────────────────────────────────"
|
||||
echo " Avvio Portale Clienti"
|
||||
echo "────────────────────────────────────────"
|
||||
|
||||
# ─────────────────────────────────────────────
|
||||
# 1. Installa le dipendenze PHP con Composer
|
||||
# --no-interaction → niente domande interattive
|
||||
# --optimize-autoloader → più veloce in produzione
|
||||
# ─────────────────────────────────────────────
|
||||
if [ ! -d "vendor" ]; then
|
||||
echo "→ vendor/ non trovata. Eseguo composer install..."
|
||||
composer install --no-interaction --optimize-autoloader
|
||||
else
|
||||
echo "→ vendor/ già presente. Salto composer install."
|
||||
fi
|
||||
|
||||
# ─────────────────────────────────────────────
|
||||
# 2. Genera APP_KEY se non è impostata
|
||||
# La chiave è usata per cifrare sessioni e cookie.
|
||||
# ─────────────────────────────────────────────
|
||||
if grep -q "^APP_KEY=$" .env 2>/dev/null || ! grep -q "^APP_KEY=" .env 2>/dev/null; then
|
||||
echo "→ APP_KEY non trovata. La genero..."
|
||||
php artisan key:generate --no-interaction
|
||||
else
|
||||
echo "→ APP_KEY già impostata."
|
||||
fi
|
||||
|
||||
# ─────────────────────────────────────────────
|
||||
# 3. Permessi sulle cartelle di storage
|
||||
# Laravel deve poter scrivere qui (log, cache, sessioni…)
|
||||
# ─────────────────────────────────────────────
|
||||
echo "→ Imposto permessi su storage/ e bootstrap/cache/"
|
||||
chmod -R 775 storage bootstrap/cache
|
||||
|
||||
# ─────────────────────────────────────────────
|
||||
# 4. Crea il link symbolico storage → public/storage
|
||||
# Necessario per servire file caricati dall'utente
|
||||
# ─────────────────────────────────────────────
|
||||
if [ ! -L "public/storage" ]; then
|
||||
echo "→ Creo symlink public/storage → storage/app/public"
|
||||
php artisan storage:link --no-interaction
|
||||
fi
|
||||
|
||||
# ─────────────────────────────────────────────
|
||||
# 5. Attende che il database sia pronto
|
||||
# MySQL impiega qualche secondo ad avviarsi.
|
||||
# ─────────────────────────────────────────────
|
||||
echo "→ Attendo che il database sia disponibile..."
|
||||
MAX_TRIES=30
|
||||
TRIES=0
|
||||
until php artisan db:monitor 2>/dev/null || [ $TRIES -ge $MAX_TRIES ]; do
|
||||
echo " Database non pronto, riprovo tra 2s... ($((TRIES+1))/$MAX_TRIES)"
|
||||
sleep 2
|
||||
TRIES=$((TRIES+1))
|
||||
done
|
||||
|
||||
if [ $TRIES -ge $MAX_TRIES ]; then
|
||||
echo "⚠ Database non raggiungibile dopo $MAX_TRIES tentativi."
|
||||
echo " Continuo comunque (potresti essere in modalità manutenzione)."
|
||||
fi
|
||||
|
||||
# ─────────────────────────────────────────────
|
||||
# 6. Esegui le migration
|
||||
# --force → necessario in ambiente non-TTY (es. Docker)
|
||||
# Le migration vengono eseguite solo se ci sono nuove
|
||||
# ─────────────────────────────────────────────
|
||||
echo "→ Eseguo le migration del database..."
|
||||
php artisan migrate --force --no-interaction
|
||||
|
||||
# ─────────────────────────────────────────────
|
||||
# 7. Esegui i seeder solo al primo avvio
|
||||
# Controlla se la tabella settings è vuota
|
||||
# ─────────────────────────────────────────────
|
||||
SETTINGS_COUNT=$(php artisan tinker --execute="echo \App\Models\Setting::count();" 2>/dev/null | tail -1 || echo "0")
|
||||
if [ "$SETTINGS_COUNT" = "0" ]; then
|
||||
echo "→ Tabella settings vuota. Eseguo i seeder..."
|
||||
php artisan db:seed --force --no-interaction
|
||||
else
|
||||
echo "→ Dati già presenti. Salto i seeder."
|
||||
fi
|
||||
|
||||
# ─────────────────────────────────────────────
|
||||
# 8. Ottimizzazioni (cache config, routes, views)
|
||||
# In development potrebbe essere più utile saltare questo,
|
||||
# in produzione invece migliora le performance.
|
||||
# ─────────────────────────────────────────────
|
||||
if [ "${APP_ENV}" = "production" ]; then
|
||||
echo "→ Ambiente produzione: ottimizzazione cache..."
|
||||
php artisan config:cache
|
||||
php artisan route:cache
|
||||
php artisan view:cache
|
||||
else
|
||||
echo "→ Ambiente development: svuoto cache esistente..."
|
||||
php artisan config:clear
|
||||
php artisan route:clear
|
||||
php artisan view:clear
|
||||
fi
|
||||
|
||||
echo "────────────────────────────────────────"
|
||||
echo " Portale Clienti pronto!"
|
||||
echo " URL: http://localhost:${NGINX_PORT:-8080}"
|
||||
echo "────────────────────────────────────────"
|
||||
|
||||
# Avvia il processo principale (php-fpm)
|
||||
exec "$@"
|
||||
34
docker/php/php.ini
Normal file
34
docker/php/php.ini
Normal file
@@ -0,0 +1,34 @@
|
||||
; ─────────────────────────────────────────────────────────────
|
||||
; Configurazione PHP personalizzata per il Portale Clienti
|
||||
; Questo file sovrascrive i default di PHP dentro il container.
|
||||
; ─────────────────────────────────────────────────────────────
|
||||
|
||||
[PHP]
|
||||
; Dimensione massima memoria per richiesta (utile per import grandi)
|
||||
memory_limit = 256M
|
||||
|
||||
; Dimensione massima upload file
|
||||
upload_max_filesize = 50M
|
||||
post_max_size = 50M
|
||||
|
||||
; Timeout di esecuzione (secondi) - aumentare per job lunghi
|
||||
max_execution_time = 300
|
||||
|
||||
; Mostra errori: ON in development, OFF in production
|
||||
; (in Docker gestiamo questo tramite APP_DEBUG nel .env)
|
||||
display_errors = Off
|
||||
log_errors = On
|
||||
error_log = /var/www/storage/logs/php_errors.log
|
||||
|
||||
[Date]
|
||||
; Fuso orario di default
|
||||
date.timezone = "Europe/Rome"
|
||||
|
||||
[opcache]
|
||||
; OPcache: compila PHP in bytecode → applicazione più veloce
|
||||
opcache.enable = 1
|
||||
opcache.memory_consumption = 128
|
||||
opcache.interned_strings_buffer = 8
|
||||
opcache.max_accelerated_files = 10000
|
||||
opcache.revalidate_freq = 0 ; In dev: 0 = ricompila sempre | In prod: 60
|
||||
opcache.save_comments = 1
|
||||
Reference in New Issue
Block a user