diff --git a/docs/it/CONTRIBUTING.md b/docs/it/CONTRIBUTING.md
new file mode 100644
index 0000000000..72f40a3e72
--- /dev/null
+++ b/docs/it/CONTRIBUTING.md
@@ -0,0 +1,429 @@
+# Contribuire
+
+Per una panoramica dell'architettura di FrankenPHP (tipi di thread, macchina a stati, confine CGO, flusso di richiesta), consultare la [documentazione interna](docs/internals.md).
+
+## Compilazione PHP
+
+### Con Docker (Linux)
+
+Costruire l'immagine Docker di sviluppo:
+
+```console
+docker build -t frankenphp-dev -f dev.Dockerfile .
+docker run --cap-add=SYS_PTRACE --security-opt seccomp=unconfined -p 8080:8080 -p 443:443 -p 443:443/udp -v $PWD:/go/src/app -it frankenphp-dev
+```
+
+L'immagine contiene i consueti strumenti di sviluppo (Go, GDB, Valgrind, Neovim...) e utilizza le seguenti posizioni di impostazione php
+
+- php.ini: `/etc/frankenphp/php.ini` Per impostazione predefinita viene fornito un file php.ini con preimpostazioni di sviluppo.
+- file di configurazione aggiuntivi: `/etc/frankenphp/php.d/*.ini`
+- estensioni php: `/usr/lib/frankenphp/modules/`
+
+Se la versione di Docker è precedente alla 23.0, la compilazione avrà esito negativo a causa di dockerignore [problema relativo al modello](https://github.com/moby/moby/pull/42676). Aggiungere a `.dockerignore`:
+
+```patch
+ !testdata/*.php
+ !testdata/*.txt
++!caddy
++!internal
+```
+
+### Senza Docker (Linux e macOS)
+
+[Seguire le istruzioni per compilare dai sorgenti](https://frankenphp.dev/docs/compile/) e passare il flag di configurazione `--debug`.
+
+## Esecuzione della suite di test
+
+```console
+export CGO_CFLAGS=-O0 -g $(php-config --includes) CGO_LDFLAGS="$(php-config --ldflags) $(php-config --libs)"
+go test -race -v ./...
+```
+
+## Modulo carrello
+
+Costruire Caddy con il modulo FrankenPHP Caddy:
+
+```console
+cd caddy/frankenphp/
+go build -tags nobadger,nomysql,nopgx
+cd ../../
+```
+
+Eseguire Caddy con il modulo FrankenPHP Caddy:
+
+```console
+cd testdata/
+../caddy/frankenphp/frankenphp run
+```
+
+Il server è in ascolto su `127.0.0.1:80`:
+
+> [!NOTE]
+> Se utilizzi Docker, dovrai associare la porta 80 del container o eseguire l'esecuzione dall'interno del container
+
+```console
+curl -vk http://127.0.0.1/phpinfo.php
+```
+
+## Server di prova minimo
+
+Costruire il server di test minimo:
+
+```console
+cd internal/testserver/
+go build
+cd ../../
+```
+
+Eseguire il server di prova:
+
+```console
+cd testdata/
+../internal/testserver/testserver
+```
+
+Il server è in ascolto su `127.0.0.1:8080`:
+
+```console
+curl -v http://127.0.0.1:8080/phpinfo.php
+```
+
+## Sviluppo su Windows
+
+1. Configurare Git per utilizzare sempre le terminazioni di riga `lf`
+
+ ```powershell
+ git config --global core.autocrlf false
+ git config --global core.eol lf
+ ```
+
+2. Installare Visual Studio, Git e Go:
+
+ ```powershell
+ winget install -e --id Microsoft.VisualStudio.2022.Community --override "--passive --wait --add Microsoft.VisualStudio.Workload.NativeDesktop --add Microsoft.VisualStudio.Component.VC.Llvm.Clang --includeRecommended"
+ winget install -e --id GoLang.Go
+ winget install -e --id Git.Git
+ ```
+
+3. Installare vcpkg:
+
+ ```powershell
+ cd C:\
+ git clone https://github.com/microsoft/vcpkg
+ .\vcpkg\bootstrap-vcpkg.bat
+ ```
+
+4. [Scaricare l'ultima versione della libreria watcher per Windows](https://github.com/e-dant/watcher/releases) ed estraila in una cartella denominata `C:\watcher`
+5. [Scaricare l'ultima versione **Thread Safe** di PHP e di PHP SDK per Windows](https://windows.php.net/download/), estraili nelle cartelle denominate `C:\php` e `C:\php-devel`
+6. Clonare il repository Git di FrankenPHP:
+
+ ```powershell
+ git clone https://github.com/php/frankenphp C:\frankenphp
+ cd C:\frankenphp
+ ```
+
+7. Installare le dipendenze:
+
+ ```powershell
+ C:\vcpkg\vcpkg.exe install
+ ```
+
+8. Configurare le variabili di ambiente necessarie (PowerShell):
+
+ ```powershell
+ $env:PATH += ';C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Tools\Llvm\bin'
+ $env:CC = 'clang'
+ $env:CXX = 'clang++'
+ $env:CGO_CFLAGS = "-O0 -g -IC:\frankenphp\vcpkg_installed\x64-windows\include -IC:\watcher -IC:\php-devel\include -IC:\php-devel\include\main -IC:\php-devel\include\TSRM -IC:\php-devel\include\Zend -IC:\php-devel\include\ext"
+ $env:CGO_LDFLAGS = '-LC:\frankenphp\vcpkg_installed\x64-windows\lib -lbrotlienc -LC:\watcher -llibwatcher-c -LC:\php -LC:\php-devel\lib -lphp8ts -lphp8embed'
+ ```
+
+9. Eseguire i test:
+
+ ```powershell
+ go test -race -ldflags '-extldflags="-fuse-ld=lld"' ./...
+ cd caddy
+ go test -race -ldflags '-extldflags="-fuse-ld=lld"' -tags nobadger,nomysql,nopgx ./...
+ cd ..
+ ```
+
+10. Costruire il binario:
+
+ ```powershell
+ cd caddy/frankenphp
+ go build -ldflags '-extldflags="-fuse-ld=lld"' -tags nobadger,nomysql,nopgx
+ cd ../..
+ ```
+
+## Creazione di immagini Docker localmente
+
+Stampare il piano di compilazione:
+
+```console
+docker buildx bake -f docker-bake.hcl --print
+```
+
+Creare immagini FrankenPHP per amd64 localmente:
+
+```console
+docker buildx bake -f docker-bake.hcl --pull --load --set "*.platform=linux/amd64"
+```
+
+Creare immagini FrankenPHP per arm64 localmente:
+
+```console
+docker buildx bake -f docker-bake.hcl --pull --load --set "*.platform=linux/arm64"
+```
+
+Creare immagini FrankenPHP da zero per arm64 e amd64 e inviale a Docker Hub:
+
+```console
+docker buildx bake -f docker-bake.hcl --pull --no-cache --push
+```
+
+## Debug degli errori di segmentazione con build statiche
+
+1. Scaricare la versione di debug del binario FrankenPHP da GitHub o creare la propria build statica personalizzata includendo i simboli di debug:
+
+ ```console
+ docker buildx bake \
+ --load \
+ --set static-builder.args.DEBUG_SYMBOLS=1 \
+ --set "static-builder.platform=linux/amd64" \
+ static-builder
+ docker cp $(docker create --name static-builder-musl dunglas/frankenphp:static-builder-musl):/go/src/app/dist/frankenphp-linux-$(uname -m) frankenphp
+ ```
+
+2. Sostituire la versione corrente di `frankenphp` con l'eseguibile di debug FrankenPHP
+3. Avviare FrankenPHP come al solito (in alternativa si può avviare direttamente FrankenPHP con GDB: `gdb --args frankenphp run`)
+4. Accedere al processo con GDB:
+
+ ```console
+ gdb -p `pidof frankenphp`
+ ```
+
+5. Se necessario, digitare `continue` nella shell GDB
+6. Mandare in crash FrankenPHP
+7. Digitarere `bt` nella shell GDB
+8. Copiare l'output
+
+## Debug degli errori di segmentazione nelle azioni GitHub
+
+1. Aprire `.github/workflows/tests.yml`
+2. Abilitare i simboli di debug PHP
+
+ ```patch
+ - uses: shivammathur/setup-php@v2
+ # ...
+ env:
+ phpts: ts
+ + debug: true
+ ```
+
+3. Abilitare `tmate` per connettersi al contenitore
+
+ ```patch
+ - name: Set CGO flags
+ run: echo "CGO_CFLAGS=-O0 -g $(php-config --includes)" >> "$GITHUB_ENV"
+ + - run: |
+ + sudo apt install gdb
+ + mkdir -p /home/runner/.config/gdb/
+ + printf "set auto-load safe-path /\nhandle SIG34 nostop noprint pass" > /home/runner/.config/gdb/gdbinit
+ + - uses: mxschmitt/action-tmate@v3
+ ```
+
+4. Connettersi al contenitore
+5. Aprire `frankenphp.go`
+6. Abilitare `cgosymbolizer`
+
+ ```patch
+ - //_ "github.com/ianlancetaylor/cgosymbolizer"
+ + _ "github.com/ianlancetaylor/cgosymbolizer"
+ ```
+
+7. Scaricare il modulo: `go get`
+8. Nel contenitore è possibile utilizzare GDB e simili:
+
+ ```console
+ go test -tags -c -ldflags=-w
+ gdb --args frankenphp.test -test.run ^MyTest$
+ ```
+
+9. Una volta risolto il bug, annullare tutte queste modifiche
+
+## Configurazione dell'ambiente di sviluppo (WSL/Unix)
+
+### Configurazione iniziale
+
+Seguire le istruzioni in [compilazione dai sorgenti](https://frankenphp.dev/docs/compile/).
+I passaggi presuppongono il seguente ambiente:
+
+- Go installato su `/usr/local/go`
+- Sorgente PHP clonato in `~/php-src`
+- PHP creato in: `/usr/local/bin/php`
+- Sorgente FrankenPHP clonata in `~/frankenphp`
+
+### Configurazione CLion per sviluppo di colla CGO/fonte PHP
+
+1. Installare CLion (sul sistema operativo host)
+
+- Scaricare da [JetBrains](https://www.jetbrains.com/clion/download/)
+ - Avviare (se su Windows, in WSL):
+
+ ```bash
+ clion &>/dev/null
+ ```
+
+2. Aprire il progetto in CLion
+
+- Aprire CLion → Open → Selezionare la cartella `~/frankenphp`
+ - Aggiungere una catena di build: Impostazioni → Compilazione, Esecuzione, Distribuzione → Destinazioni di build personalizzate
+ - Selezionare un target di build qualsiasi, in `Build` impostare uno strumento esterno (chiamalo ad esempio go build)
+ - Impostare uno script wrapper che crei frankenphp, chiamato `go_compile_frankenphp.sh`
+
+ ```bash
+ CGO_CFLAGS="-O0 -g" ./go.sh
+ ```
+
+- In Programma, selezionare `go_compile_frankenphp.sh`
+ - Lasciare gli argomenti vuoti
+ - Cartella di lavoro: `~/frankenphp/caddy/frankenphp`
+
+3. Configurare le destinazioni della corsa
+
+- Andare su Esegui → Modifica configurazioni
+ - Crea:
+ -frankenphp:
+ - Tipo: applicazione nativa
+ - Target: seleziona il target `go build` creato in precedenza
+ - Eseguibile: `~/frankenphp/caddy/frankenphp/frankenphp`
+ - Argomenti: gli argomenti con cui su vuole avviare Frankenphp, ad es. `php-cli test.php`
+
+4. Eseguire il debug dei file Go da CLion
+
+- Fare clic con il tasto destro su un file \*.go nella vista Progetto a sinistra
+ - Sostituire il tipo di file → C/C++
+
+Ora si possono inserire punti di interruzione nei file C, C++ e Go.
+ Per ottenere l'evidenziazione della sintassi per le importazioni da php-src, potrebbe essere necessario comunicare a CLion i percorsi di inclusione. Creare un
+ File `compile_flags.txt` in `~/frankenphp` con il seguente contenuto:
+
+ ```gcc
+ -I/usr/local/include/php
+ -I/usr/local/include/php/Zend
+ -I/usr/local/include/php/main
+ -I/usr/local/include/php/TSRM
+ ```
+
+---
+
+### Configurazione di GoLand per lo sviluppo di FrankenPHP
+
+Utilizzare GoLand per lo sviluppo Go primario, ma il debugger non può eseguire il debug del codice C.
+
+1. Installare GoLand (sul sistema operativo host)
+
+- Scaricare da [JetBrains](https://www.jetbrains.com/go/download/)
+
+ ```bash
+ goland &>/dev/null
+ ```
+
+2. Aprire in GoLand
+
+- Avviare GoLand → Apri → Selezionare la cartella `~/frankenphp`
+
+---
+
+### Configurazione di Go
+
+- Selezionare Go Build
+ - Nome `frankenphp`
+ - Tipo di esecuzione: Directory
+- Cartella: `~/frankenphp/caddy/frankenphp`
+- Cartella di output: `~/frankenphp/caddy/frankenphp`
+- Cartella di lavoro: `~/frankenphp/caddy/frankenphp`
+- Ambiente (da adattare per il proprio output $(php-config ...)):
+ `CGO_CFLAGS=-O0 -g -I/usr/local/include/php -I/usr/local/include/php/main -I/usr/local/include/php/TSRM -I/usr/local/include/php/Zend -I/usr/local/include/php/ext -I/usr/local/include/php/ext/date/lib;CGO_LDFLAGS=-lm -lpthread -lsqlite3 -lxml2 -lbrotlienc -lbrotlidec -lbrotlicommon -lwatcher`
+- Vai agli argomenti dello strumento: `-tags=nobadger,nomysql,nopgx`
+- Argomenti del programma: ad es. `php-cli -i`
+
+Per eseguire il debug dei file C da GoLand
+
+- Fare clic con il tasto destro su un file \*.c nella vista Progetto a sinistra
+- Sostituire il tipo di file → Go
+
+Ora si possono inserire punti di interruzione nei file C, C++ e Go.
+
+---
+
+### Configurazione di GoLand su Windows
+
+1. Seguire la [sezione Sviluppo Windows](#windows-development)
+
+2. Installare GoLand
+
+- Scaricare da [JetBrains](https://www.jetbrains.com/go/download/)
+ - Avviare GoLand
+
+3. Aprire in GoLand
+
+- Selezionare **Apri** → Scegliere la cartella in cui `frankenphp` è stato clonato
+
+4. Configurare Go Build
+
+- Andare a **Esegui** → **Modifica configurazioni**
+ - Fare clic su **++** e seleziona **Vai a costruire**
+ - Nome: `frankenphp`
+ - Tipo di esecuzione: **Directory**
+ - Cartella: `.\caddy\frankenphp`
+ - Cartella di output: `.\caddy\frankenphp`
+ - Cartella di lavoro: `.\caddy\frankenphp`
+ - Vai agli argomenti dello strumento: `-tags=nobadger,nomysql,nopgx`
+ - Variabili d'ambiente: vedere la [sezione Sviluppo Windows](#windows-development)
+ - Argomenti del programma: ad es. `php-server`
+
+---
+
+### Note di debug e integrazione
+
+- Utilizzare CLion per eseguire il debug degli interni PHP e del codice colla `cgo`
+- Utilizza GoLand per lo sviluppo e il debugging primario di Go
+- FrankenPHP può essere aggiunto come configurazione di esecuzione in CLion per il debug C/Go unificato, se necessario, ma l'evidenziazione della sintassi non funzionerà nei file Go
+
+## Risorse varie per lo sviluppo
+
+- [Embed PHP in uWSGI](https://github.com/unbit/uwsgi/blob/master/plugins/php/php_plugin.c)
+- [Embed PHP nell'unità NGINX](https://github.com/nginx/unit/blob/master/src/nxt_php_sapi.c)
+- [Embed PHP in Go (go-php)](https://github.com/deuill/go-php)
+- [Embed PHP in Go (GoEmPHP)](https://github.com/mikespook/goemphp)
+- [Embed PHP in C++](https://gist.github.com/paresy/3cbd4c6a469511ac7479aa0e7c42fea7)
+- [Estensione ed Embed di PHP di Sara Golemon](https://books.google.fr/books?id=zMbGvK17_tYC&pg=PA254&lpg=PA254#v=onepage&q&f=false)
+- [CWhat the heck is TSRMLS_CC, anyway?](http://blog.golemon.com/2006/06/what-heck-is-tsrmlscc-anyway.html)
+- [Binding SDL](https://pkg.go.dev/github.com/veandco/go-sdl2@v0.4.21/sdl#Main)
+
+## Risorse relative a Docker
+
+- [Definizione del file Bake](https://docs.docker.com/build/customize/bake/file-definition/)
+-[`docker buildx build`](https://docs.docker.com/engine/reference/commandline/buildx_build/)
+
+## Comando utile
+
+```console
+apk add strace util-linux gdb
+strace -e 'trace=!futex,epoll_ctl,epoll_pwait,tgkill,rt_sigreturn' -p 1
+```
+
+## Tradurre la documentazione
+
+Per tradurre la documentazione e il sito in una nuova lingua,
+seguire questi passaggi:
+
+1. Creare una nuova cartella chiamata con il codice ISO a due caratteri della lingua nella cartella `docs/` di questo repository
+2. Copiare tutti i file `.md` nella radice della cartella `docs/` nella nuova cartella (utilizzare sempre la versione inglese come fonte per la traduzione, poiché è sempre aggiornata)
+3. Copiare i file `README.md` e `CONTRIBUTING.md` dalla cartella principale alla nuova cartella
+4. Tradurre il contenuto dei file, ma non modificare i nomi dei file, inoltre non tradurre le stringhe che iniziano con `> [!` (è un markup speciale per GitHub)
+5. Creare una pull request con le traduzioni
+6. Nel [repository del sito](https://github.com/dunglas/frankenphp-website/tree/main), copiare e tradurre i file di traduzione nelle cartelle `content/`, `data/` e `i18n/`
+7. Tradurre i valori nel file YAML creato
+8. Aprire una pull request sul repository del sito
diff --git a/docs/it/README.md b/docs/it/README.md
new file mode 100644
index 0000000000..65cb7b7cd6
--- /dev/null
+++ b/docs/it/README.md
@@ -0,0 +1,192 @@
+# FrankenPHP: App Server moderno per PHP
+
+
+
+FrankenPHP è un server di applicazioni per PHP costruito sul server web [Caddy](https://caddyserver.com/).
+
+FrankenPHP dà superpoteri alle app PHP grazie alle sue straordinarie funzionalità: [_Early Hints_](https://frankenphp.dev/docs/early-hints/), [modalità worker](https://frankenphp.dev/docs/worker/), [funzionalità in tempo reale](https://frankenphp.dev/docs/mercure/), [ricaricamento a caldo](https://frankenphp.dev/docs/hot-reload/), supporto automatico HTTPS, HTTP/2 e HTTP/3...
+
+FrankenPHP funziona con qualsiasi app PHP e rende i progetti Laravel e Symfony più veloci che mai grazie alle loro integrazioni ufficiali con la modalità worker.
+
+FrankenPHP può anche essere utilizzato come libreria Go autonoma per incorporare PHP in qualsiasi app utilizzando `net/http`.
+
+[**Ulteriori informazioni** su _frankenphp.dev_](https://frankenphp.dev) e in questa presentazione:
+
+
+
+## Iniziare
+
+### Installare lo script
+
+Su Linux e macOS, copiare questa riga nel terminale per installare automaticamente
+una versione adatta alla piattaforma usata:
+
+```console
+curl https://frankenphp.dev/install.sh | sh
+```
+
+Su Windows, eseguire in PowerShell:
+
+```powershell
+irm https://frankenphp.dev/install.ps1 | iex
+```
+
+### Binario autonomo
+
+Forniamo i binari FrankenPHP per Linux, macOS e Windows
+con [PHP 8.5](https://www.php.net/releases/8.5/).
+
+I binari Linux sono collegati staticamente, quindi possono essere utilizzati su qualsiasi distribuzione Linux senza installare alcuna dipendenza. Anche i file binari di macOS sono autonomi.
+Contengono le estensioni PHP più popolari.
+Gli archivi di Windows contengono il binario PHP ufficiale per Windows.
+
+[Scaricare FrankenPHP](https://github.com/php/frankenphp/releases)
+
+### Pacchetti rpm
+
+I nostri manutentori offrono pacchetti rpm per tutti i sistemi che utilizzano `dnf`. Per installare, eseguire:
+
+```console
+sudo dnf install https://rpm.henderkes.com/static-php-1-0.noarch.rpm
+sudo dnf module enable php-zts:static-8.5 # sono disponibili da 8.2 a 8.5
+sudo dnf install frankenphp
+```
+
+**Installazione delle estensioni:** `sudo dnf install php-zts-`
+
+Per le estensioni non disponibili per impostazione predefinita, utilizzare [PIE](https://github.com/php/pie):
+
+```console
+sudo dnf install pie-zts
+sudo pie-zts install asgrim/example-pie-extension
+```
+
+### Pacchetti deb
+
+I nostri manutentori offrono pacchetti deb per tutti i sistemi che utilizzano `apt`. Per installare, eseguire:
+
+```console
+VERSION=85 # sono disponibili da 82 a 85
+sudo curl https://pkg.henderkes.com/api/packages/${VERSION}/debian/repository.key -o /etc/apt/keyrings/static-php${VERSION}.asc
+echo "deb [signed-by=/etc/apt/keyrings/static-php${VERSION}.asc] https://pkg.henderkes.com/api/packages/${VERSION}/debian php-zts main" | sudo tee -a /etc/apt/sources.list.d/static-php${VERSION}.list
+sudo apt update
+sudo apt install frankenphp
+```
+
+**Installazione delle estensioni:** `sudo apt install php-zts-`
+
+Per le estensioni non disponibili per impostazione predefinita, utilizzare [PIE](https://github.com/php/pie):
+
+```console
+sudo apt install pie-zts
+sudo pie-zts install asgrim/example-pie-extension
+```
+
+### Pacchetti apk
+
+I nostri manutentori offrono pacchetti apk per tutti i sistemi che utilizzano `apk`. Per installare, eseguire:
+
+```console
+VERSION=85 # sono disponibili da 82 a 85
+echo "https://pkg.henderkes.com/api/packages/${VERSION}/alpine/main/php-zts" | sudo tee -a /etc/apk/repositories
+KEYFILE=$(curl -sJOw '%{filename_effective}' https://pkg.henderkes.com/api/packages/${VERSION}/alpine/key)
+sudo mv ${KEYFILE} /etc/apk/keys/ &&
+sudo apk update &&
+sudo apk add frankenphp
+```
+
+**Installazione delle estensioni:** `sudo apk add php-zts-`
+
+Per le estensioni non disponibili per impostazione predefinita, utilizzare [PIE](https://github.com/php/pie):
+
+```console
+sudo apk add pie-zts
+sudo pie-zts install asgrim/example-pie-extension
+```
+
+### Birra fatta in casa
+
+FrankenPHP è disponibile anche come pacchetto [Homebrew](https://brew.sh) per macOS e Linux.
+
+```console
+brew install dunglas/frankenphp/frankenphp
+```
+
+**Installazione delle estensioni:** utilizzare [PIE](https://github.com/php/pie).
+
+### Utilizzo
+
+Per servire il contenuto della cartella corrente, eseguire:
+
+```console
+frankenphp php-server
+```
+
+Si possono anche eseguire script da riga di comando con:
+
+```console
+frankenphp php-cli /path/to/your/script.php
+```
+
+Per i pacchetti deb e rpm, si può anche avviare il servizio systemd:
+
+```console
+sudo systemctl start frankenphp
+```
+
+### Docker
+
+In alternativa, sono disponibili [Immagini Docker](https://frankenphp.dev/docs/docker/):
+
+```console
+docker run -v .:/app/public \
+ -p 80:80 -p 443:443 -p 443:443/udp \
+ dunglas/frankenphp
+```
+
+Aprire `https://localhost` e buon divertimento!
+
+> [!TIP]
+>
+> Non tentare di utilizzare `https://127.0.0.1`. Usare `https://localhost` e accettare il certificato autofirmato.
+> Utilizzare la [variabile di ambiente `SERVER_NAME`](docs/config.md#environment-variables) per modificare il dominio da utilizzare.
+
+## Documenti
+
+- [Modalità classica](https://frankenphp.dev/docs/classic/)
+- [Modalità worker](https://frankenphp.dev/docs/worker/)
+- [Migrazione da Nginx/PHP-FPM](https://frankenphp.dev/docs/migrate/)
+- [Supporto per Early Hints (codice di stato HTTP 103)](https://frankenphp.dev/docs/early-hints/)
+- [Real time](https://frankenphp.dev/docs/mercure/)
+- [Log](https://frankenphp.dev/docs/logging/)
+- [Ricaricamento a caldo](https://frankenphp.dev/docs/hot-reload/)
+- [Gestione efficiente di file statici di grandi dimensioni](https://frankenphp.dev/docs/x-sendfile/)
+- [Configurazione](https://frankenphp.dev/docs/config/)
+- [Scrittura delle estensioni PHP in Go](https://frankenphp.dev/docs/extensions/)
+- [Immagini Docker](https://frankenphp.dev/docs/docker/)
+- [Deploy in produzione](https://frankenphp.dev/docs/production/)
+- [Ottimizzazione delle prestazioni](https://frankenphp.dev/docs/performance/)
+- [Crea **app PHP autonome** e autoeseguibili](https://frankenphp.dev/docs/embed/)
+- [Creare file binari statici](https://frankenphp.dev/docs/static/)
+- [Compilare da sorgente](https://frankenphp.dev/docs/compile/)
+- [Osservabilità](https://frankenphp.dev/docs/observability/)
+- [Integrazione WordPress](https://frankenphp.dev/docs/wordpress/)
+- [Integrazione Symfony](https://frankenphp.dev/docs/symfony/)
+- [Integrazione Laravel](https://frankenphp.dev/docs/laravel/)
+- [Problemi noti](https://frankenphp.dev/docs/known-issues/)
+- [App demo (Symfony) e benchmark](https://github.com/dunglas/frankenphp-demo)
+- [Documentazione della libreria Go](https://pkg.go.dev/github.com/dunglas/frankenphp)
+- [Contributi e debug](https://frankenphp.dev/docs/contributing/)
+- [Interni (panoramica dell'architettura)](docs/internals.md)
+
+## Esempi e scheletri
+
+- [Symfony](https://frankenphp.dev/docs/symfony/)
+- [API Platform](https://api-platform.com/docs/symfony)
+- [Laravel](https://frankenphp.dev/docs/laravel/)
+- [Sulu](https://sulu.io/blog/running-sulu-with-frankenphp)
+- [WordPress](https://github.com/StephenMiracle/frankenwp)
+- [Drupal](https://github.com/dunglas/frankenphp-drupal)
+- [Joomla](https://github.com/alexandreelise/frankenphp-joomla)
+- [TYPO3](https://github.com/ochorocho/franken-typo3)
+- [Magento2](https://github.com/ekino/frankenphp-magento2)
diff --git a/docs/it/classic.md b/docs/it/classic.md
new file mode 100644
index 0000000000..4c0858adac
--- /dev/null
+++ b/docs/it/classic.md
@@ -0,0 +1,11 @@
+# Usare la modalità classica
+
+Senza alcuna configurazione aggiuntiva, FrankenPHP funziona in modalità classica. In questa modalità, FrankenPHP funziona come un tradizionale server PHP, servendo direttamente i file PHP. Ciò lo rende un sostituto perfetto per PHP-FPM o Apache con mod_php.
+
+Similmente a Caddy, FrankenPHP accetta un numero illimitato di connessioni e utilizza un [numero fisso di thread](config.md#caddyfile-config) per servirle. Il numero di connessioni accettate e in coda è limitato solo dalle risorse di sistema disponibili.
+Il pool di thread PHP funziona con un numero fisso di thread inizializzati all'avvio, paragonabile alla modalità statica di PHP-FPM. È anche possibile consentire ai thread di [ridimensionarsi automaticamente in fase di esecuzione](performance.md#max_threads), in modo simile alla modalità dinamica di PHP-FPM.
+
+Le connessioni in coda attenderanno indefinitamente finché non sarà disponibile un thread PHP per servirle. Per evitarlo, si può utilizzare max_wait_time nella [configurazione](config.md#caddyfile-config) globale di FrankenPHP per limitare la durata di attesa di una richiesta per un thread PHP libero prima di essere rifiutata.
+Inoltre, si può impostare un [timeout di scrittura](https://caddyserver.com/docs/caddyfile/options#timeouts) ragionevole.
+
+Ogni istanza Caddy avvierà solo un pool di thread FrankenPHP, che sarà condiviso tra tutti i blocchi `php_server`.
diff --git a/docs/it/compile.md b/docs/it/compile.md
new file mode 100644
index 0000000000..17319aab27
--- /dev/null
+++ b/docs/it/compile.md
@@ -0,0 +1,133 @@
+# Compilazione dai sorgenti
+
+Questo documento spiega come creare un binario FrankenPHP che caricherà PHP come libreria condivisa.
+Questo è il metodo consigliato.
+
+In alternativa, è possibile creare anche [build completamente e prevalentemente statiche](static.md).
+
+## Instalalre PHP
+
+FrankenPHP è compatibile con PHP 8.2 e versioni successive.
+
+### Con Homebrew (Linux e Mac)
+
+Il modo più semplice per installare una versione di libphp compatibile con FrankenPHP è utilizzare i pacchetti ZTS forniti da [Homebrew PHP](https://github.com/shivammathur/homebrew-php).
+
+Innanzitutto, se non lo hai già fatto, installa [Homebrew](https://brew.sh).
+
+Quindi, installa la variante ZTS di PHP, Brotli (opzionale, per il supporto della compressione) e watcher (opzionale, per il rilevamento delle modifiche ai file):
+
+```console
+brew install shivammathur/php/php-zts brotli watcher
+brew link --overwrite --force shivammathur/php/php-zts
+```
+
+### Compilare PHP
+
+In alternativa, si può compilare PHP dai sorgenti con le opzioni necessarie a FrankenPHP, seguendo questi passaggi.
+
+Per prima cosa, [recuperare i sorgenti PHP](https://www.php.net/downloads.php) ed estrarli:
+
+```console
+tar xf php-*
+cd php-*/
+```
+
+Quindi, eseguire lo script `configure` con le opzioni necessarie per la propria piattaforma.
+I seguenti flag `./configure` sono obbligatori, ma se ne possono aggiungerne altri, ad esempio, per compilare estensioni o funzionalità aggiuntive.
+
+#### Linux e FreeBSD
+
+```console
+./configure \
+ --enable-embed \
+ --enable-zts \
+ --disable-zend-signals \
+ --enable-zend-max-execution-timers
+```
+
+#### Mac
+
+Utilizzare il gestore pacchetti [Homebrew](https://brew.sh/) per installare le dipendenze obbligatorie e facoltative:
+
+```console
+brew install libiconv bison brotli re2c pkg-config watcher
+echo 'export PATH="/opt/homebrew/opt/bison/bin:$PATH"' >> ~/.zshrc
+```
+
+Quindi eseguire lo script di configurazione:
+
+```console
+./configure \
+ --enable-embed \
+ --enable-zts \
+ --disable-zend-signals \
+ --with-iconv=/opt/homebrew/opt/libiconv/
+```
+
+#### Compilare PHP
+
+Infine, compilare e installare PHP:
+
+```console
+make -j"$(getconf _NPROCESSORS_ONLN)"
+sudo make install
+```
+
+## Installare dipendenze opzionali
+
+Alcune funzionalità di FrankenPHP dipendono da dipendenze di sistema opzionali che devono essere installate.
+In alternativa, queste funzionalità possono essere disabilitate passando i tag di build al compilatore Go.
+
+| Caratteristica | Dipendenza | Crea tag per disabilitarlo |
+| ------------------------------- | ------------------------------------------------------------------------------------------------------------ | ----------------------- |
+| Compressione Brotli | [Brotli](https://github.com/google/brotli) | nobrotli |
+| Riavvia i worker alla modifica del file | [Osservatore C](https://github.com/e-dant/watcher/tree/release/watcher-c) | nessun osservatore |
+| [Mercure](mercure.md) | [Libreria Mercure Go](https://pkg.go.dev/github.com/dunglas/mercure) (installata automaticamente, licenza AGPL) | nomercura |
+
+## Compilare l'app Go
+
+Ora si può creare il file binario finale.
+
+### Utilizzo di xcaddy
+
+Il modo consigliato è utilizzare [xcaddy](https://github.com/caddyserver/xcaddy) per compilare FrankenPHP.
+`xcaddy` consente inoltre di aggiungere facilmente [moduli Caddy personalizzati](https://caddyserver.com/docs/modules/) ed estensioni FrankenPHP:
+
+```console
+CGO_ENABLED=1 \
+XCADDY_GO_BUILD_FLAGS="-ldflags='-w -s' -tags=nobadger,nomysql,nopgx" \
+CGO_CFLAGS=$(php-config --includes) \
+CGO_LDFLAGS="$(php-config --ldflags) $(php-config --libs)" \
+xcaddy build \
+ --output frankenphp \
+ --with github.com/dunglas/frankenphp/caddy \
+ --with github.com/dunglas/mercure/caddy \
+ --with github.com/dunglas/vulcain/caddy \
+ --with github.com/dunglas/caddy-cbrotli
+ # Add extra Caddy modules and FrankenPHP extensions here
+ # optionally, if you would like to compile from your frankenphp sources:
+ # --with github.com/dunglas/frankenphp=$(pwd) \
+ # --with github.com/dunglas/frankenphp/caddy=$(pwd)/caddy
+
+```
+
+> [!TIP]
+>
+> Se stai usando musl libc (il valore predefinito su Alpine Linux) e Symfony,
+> potrebbe essere necessario aumentare la dimensione dello stack predefinita.
+> Altrimenti potresti ricevere errori come `PHP Fatal error: Maximum call stack size of 83360 bytes reached during compilation. Try splitting expression`
+>
+> Per fare ciò, cambiare la variabile d'ambiente `XCADDY_GO_BUILD_FLAGS` in qualcosa di simile
+> `XCADDY_GO_BUILD_FLAGS=$'-ldflags "-w -s -extldflags \'-Wl,-z,stack-size=0x80000\'"'`
+> (modificare il valore della dimensione dello stack in base alle esigenze dell'app).
+
+### Senza xcaddy
+
+In alternativa, è possibile compilare FrankenPHP senza `xcaddy` utilizzando direttamente il comando `go`:
+
+```console
+curl -L https://github.com/php/frankenphp/archive/refs/heads/main.tar.gz | tar xz
+cd frankenphp-main/caddy/frankenphp
+CGO_CFLAGS=$(php-config --includes) CGO_LDFLAGS="$(php-config --ldflags) $(php-config --libs)" go build -tags=nobadger,nomysql,nopgx
+```
diff --git a/docs/it/config.md b/docs/it/config.md
new file mode 100644
index 0000000000..87e72ee3b2
--- /dev/null
+++ b/docs/it/config.md
@@ -0,0 +1,443 @@
+# Configurazione
+
+FrankenPHP, Caddy e i moduli [Mercure](mercure.md) e [Vulcain](https://vulcain.rocks) possono essere configurati utilizzando [i formati supportati da Caddy](https://caddyserver.com/docs/getting-started#your-first-config).
+
+Il formato più comune è `Caddyfile`, che è un formato di testo semplice e leggibile.
+Per impostazione predefinita, FrankenPHP cercherà un `Caddyfile` nella cartella corrente.
+È possibile specificare un percorso personalizzato con l'opzione `-c` o `--config`.
+
+Di seguito è mostrato un `Caddyfile` minimo per servire un'applicazione PHP:
+
+```caddyfile
+# Il nome host a cui rispondere
+localhost
+
+# Facolativo,il percorso da cui servire i file, altrimenti sarà usato il percorso attuale
+#root public/
+php_server
+```
+
+Viene fornito un `Caddyfile` più avanzato che abilita più funzionalità e fornisce comode variabili di ambiente [nel repository FrankenPHP](https://github.com/php/frankenphp/blob/main/caddy/frankenphp/Caddyfile),
+e con immagini Docker.
+
+PHP stesso può essere configurato [utilizzando un file `php.ini`](https://www.php.net/manual/en/configuration.file.php).
+
+A seconda del metodo di installazione, FrankenPHP e l'interprete PHP cercheranno i file di configurazione nelle posizioni descritte di seguito.
+
+## Docker
+
+FrankenPHP:
+
+- `/etc/frankenphp/Caddyfile`: il file di configurazione principale
+- `/etc/frankenphp/Caddyfile.d/*.caddyfile`: file di configurazione aggiuntivi che vengono caricati automaticamente
+
+PHP:
+
+- `php.ini`: `/usr/local/etc/php/php.ini` (per impostazione predefinita non è fornito `php.ini`)
+- file di configurazione aggiuntivi: `/usr/local/etc/php/conf.d/*.ini`
+- Estensioni PHP: `/usr/local/lib/php/extensions/no-debug-zts-/`
+- Dovresti copiare un modello ufficiale fornito dal progetto PHP:
+
+```dockerfile
+FROM dunglas/frankenphp
+
+# Production:
+RUN cp $PHP_INI_DIR/php.ini-production $PHP_INI_DIR/php.ini
+
+# Or development:
+RUN cp $PHP_INI_DIR/php.ini-development $PHP_INI_DIR/php.ini
+```
+
+## Pacchetti RPM e Debian
+
+FrankenPHP:
+
+- `/etc/frankenphp/Caddyfile`: il file di configurazione principale
+- `/etc/frankenphp/Caddyfile.d/*.caddyfile`: file di configurazione aggiuntivi che vengono caricati automaticamente
+
+PHP:
+
+- `php.ini`: `/etc/php-zts/php.ini` (per impostazione predefinita viene fornito un file `php.ini` con preimpostazioni di produzione)
+- file di configurazione aggiuntivi: `/etc/php-zts/conf.d/*.ini`
+
+## Binario statico
+
+FrankenPHP:
+
+- Nella cartella di lavoro corrente: `Caddyfile`
+
+PHP:
+
+- `php.ini`: la cartella in cui viene eseguito `frankenphp run` o `frankenphp php-server`, quindi `/etc/frankenphp/php.ini`
+- file di configurazione aggiuntivi: `/etc/frankenphp/php.d/*.ini`
+- Estensioni PHP: non possono essere caricate, raggruppatele nel binario stesso
+- copia uno dei `php.ini-production` o `php.ini-development` forniti [nei sorgenti PHP](https://github.com/php/php-src/).
+
+## Configurazione Caddyfile
+
+`php_server` o `php` [direttive HTTP](https://caddyserver.com/docs/caddyfile/concepts#directives) possono essere utilizzate all'interno dei blocchi del sito per servire l'app PHP.
+
+Esempio minimo:
+
+```caddyfile
+localhost {
+ # Enable compression (optional)
+ encode zstd br gzip
+ # Execute PHP files in the current directory and serve assets
+ php_server
+}
+```
+
+Puoi anche configurare esplicitamente FrankenPHP utilizzando l'[opzione globale](https://caddyserver.com/docs/caddyfile/concepts#global-options) `frankenphp`:
+
+```caddyfile
+{
+ frankenphp {
+ num_threads # Sets the number of PHP threads to start. Default: 2x the number of available CPUs.
+ max_threads # Limits the number of additional PHP threads that can be started at runtime. Default: num_threads. Can be set to 'auto'.
+ max_wait_time # Sets the maximum time a request may wait for a free PHP thread before timing out. Default: disabled.
+ max_idle_time # Sets the maximum time an autoscaled thread may be idle before being deactivated. Default: 5s.
+ max_requests # (experimental) Sets the maximum number of requests a PHP thread will handle before being restarted, useful for mitigating memory leaks. Applies to both regular and worker threads. Default: 0 (unlimited).
+ php_ini # Set a php.ini directive. Can be used several times to set multiple directives.
+ worker {
+ file # Sets the path to the worker script.
+ num # Sets the number of PHP threads to start, defaults to 2x the number of available CPUs.
+ env # Sets an extra environment variable to the given value. Can be specified more than once for multiple environment variables.
+ watch # Sets the path to watch for file changes. Can be specified more than once for multiple paths.
+ name # Sets the name of the worker, used in logs and metrics. Default: absolute path of worker file
+ max_consecutive_failures # Sets the maximum number of consecutive failures before the worker is considered unhealthy, -1 means the worker will always restart. Default: 6.
+ }
+ }
+}
+
+# ...
+```
+
+In alternativa, è possibile utilizzare la forma breve di una riga dell'opzione `worker`:
+
+```caddyfile
+{
+ frankenphp {
+ worker
+ }
+}
+
+# ...
+```
+
+Puoi anche definire più worker se servi più app sullo stesso server:
+
+```caddyfile
+app.example.com {
+ root /path/to/app/public
+ php_server {
+ root /path/to/app/public # allows for better caching
+ worker index.php
+ }
+}
+
+other.example.com {
+ root /path/to/other/public
+ php_server {
+ root /path/to/other/public
+ worker index.php
+ }
+}
+
+# ...
+```
+
+L'uso della direttiva `php_server` è generalmente ciò che serve,
+ma se si ha bisogno del controllo completo, si può utilizzare la direttiva `php` di livello inferiore.
+La direttiva `php` passa tutti gli input a PHP, invece di verificare prima se
+sia un file PHP o meno. Per ulteriori informazioni, consulta la [pagina sulle prestazioni](performance.md#try_files).
+
+L'utilizzo della direttiva `php_server` equivale a questa configurazione:
+
+```caddyfile
+route {
+ # Add trailing slash for directory requests
+ @canonicalPath {
+ file {path}/index.php
+ not path */
+ }
+ redir @canonicalPath {path}/ 308
+ # If the requested file does not exist, try index files
+ @indexFiles file {
+ try_files {path} {path}/index.php index.php
+ split_path .php
+ }
+ rewrite @indexFiles {http.matchers.file.relative}
+ # FrankenPHP!
+ @phpFiles path *.php
+ php @phpFiles
+ file_server
+}
+```
+
+Le direttive `php_server` e `php` hanno le seguenti opzioni:
+
+```caddyfile
+php_server [] {
+ root # Sets the root folder to the site. Default: `root` directive.
+ split_path # Sets the substrings for splitting the URI into two parts. The first matching substring will be used to split the "path info" from the path. The first piece is suffixed with the matching substring and will be assumed as the actual resource (CGI script) name. The second piece will be set to PATH_INFO for the script to use. Default: `.php`
+ resolve_root_symlink false # Disables resolving the `root` directory to its actual value by evaluating a symbolic link, if one exists (enabled by default).
+ env # Sets an extra environment variable to the given value. Can be specified more than once for multiple environment variables.
+ file_server off # Disables the built-in file_server directive.
+ worker { # Creates a worker specific to this server. Can be specified more than once for multiple workers.
+ file # Sets the path to the worker script, can be relative to the php_server root
+ num # Sets the number of PHP threads to start, defaults to 2x the number of available
+ name # Sets the name for the worker, used in logs and metrics. Default: absolute path of worker file. Always starts with m# when defined in a php_server block.
+ watch # Sets the path to watch for file changes. Can be specified more than once for multiple paths.
+ env # Sets an extra environment variable to the given value. Can be specified more than once for multiple environment variables. Environment variables for this worker are also inherited from the php_server parent, but can be overwritten here.
+ match # match the worker to a path pattern. Overrides try_files and can only be used in the php_server directive.
+ }
+ worker # Can also use the short form like in the global frankenphp block.
+}
+```
+
+### Controllo delle modifiche ai file
+
+Poiché i worker avviano l'applicazione solo una volta e la mantengono in memoria, eventuali modifiche
+ai file PHP non si rifletteranno immediatamente.
+
+I worker possono invece essere riavviati in caso di modifiche ai file tramite la direttiva `watch`.
+Ciò è utile per gli ambienti di sviluppo.
+
+```caddyfile
+{
+ frankenphp {
+ worker {
+ file /path/to/app/public/worker.php
+ watch
+ }
+ }
+}
+```
+
+Questa funzione viene spesso utilizzata in combinazione con [ricaricamento a caldo](hot-reload.md).
+
+Se la carteòòa `watch` non è specificata, tornerà a `./**/*.{env,php,twig,yaml,yml}`,
+che controlla tutti i file `.env`, `.php`, `.twig`, `.yaml` e `.yml` nella cartella e nelle sottocartelle
+dove è stato avviato il processo FrankenPHP. Puoi invece anche specificare una o più cartelle tramite a
+[modello nome file shell](https://pkg.go.dev/path/filepath#Match):
+
+```caddyfile
+{
+ frankenphp {
+ worker {
+ file /path/to/app/public/worker.php
+ watch /path/to/app # watches all files in all subdirectories of /path/to/app
+ watch /path/to/app/*.php # watches files ending in .php in /path/to/app
+ watch /path/to/app/**/*.php # watches PHP files in /path/to/app and subdirectories
+ watch /path/to/app/**/*.{php,twig} # watches PHP and Twig files in /path/to/app and subdirectories
+ }
+ }
+}
+```
+
+- Il modello `**` indica la visione ricorsiva
+- Le cartelle possono anche essere relative (a dove viene avviato il processo FrankenPHP)
+- Se sono definiti più worker, tutti verranno riavviati quando un file cambia
+- Fare attenzione a guardare i file creati in fase di esecuzione (come i log) poiché potrebbero causare riavvii indesiderati del worker.
+
+Il file watcher è basato su [e-dant/watcher](https://github.com/e-dant/watcher).
+
+## Abbinamento del worker a un percorso
+
+Nelle applicazioni PHP tradizionali, gli script vengono sempre inseriti nella cartella pubblica.
+Questo vale anche per i worker, che vengono trattati come qualsiasi altro script PHP.
+Se si desidera invece inserire lo script worker all'esterno della cartella pubblica, lo si può fare tramite la direttiva `match`.
+
+La direttiva `match` è un'alternativa ottimizzata a `try_files` disponibile solo all'interno di `php_server` e `php`.
+L'esempio seguente servirà sempre un file nella cartella pubblica, se presente,
+altrimenti inoltrerà la richiesta al worker che corrisponde al modello di percorso.
+
+```caddyfile
+{
+ frankenphp {
+ php_server {
+ worker {
+ file /path/to/worker.php # il file può trovarsi fuori dal percorso pubblico
+ match /api/* # ogni richiesta che inizia per /api/ sarà gestita da questo worker
+ }
+ }
+ }
+}
+```
+
+## Riavvio dei thread dopo una serie di richieste (sperimentale)
+
+FrankenPHP può riavviare automaticamente i thread PHP dopo aver gestito un determinato numero di richieste.
+Quando un thread raggiunge il limite, viene riavviato completamente,
+ripulire tutta la memoria e lo stato. Altri thread continuano a servire le richieste durante il riavvio.
+
+Se noti che la memoria aumenta nel tempo, la soluzione ideale è segnalare la perdita
+all'estensione responsabile o al manutentore della libreria.
+Ma quando la soluzione dipende da una terza parte che non controlli,
+`max_requests` fornisce una soluzione pragmatica e, si spera, temporanea per la produzione:
+
+```caddyfile
+{
+ frankenphp {
+ max_requests 500
+ }
+}
+```
+
+## Variabili d'ambiente
+
+Le seguenti variabili di ambiente possono essere utilizzate per inserire le direttive Caddy in `Caddyfile` senza modificarlo:
+
+- `SERVER_NAME`: modifica [gli indirizzi su cui ascoltare](https://caddyserver.com/docs/caddyfile/concepts#addresses), i nomi host forniti verranno utilizzati anche per il certificato TLS generato
+- `SERVER_ROOT`: cambia la cartella principale del sito, il valore predefinito è `public/`
+- `CADDY_GLOBAL_OPTIONS`: inserire [opzioni globali](https://caddyserver.com/docs/caddyfile/options)
+- `FRANKENPHP_CONFIG`: inietta la configurazione nella direttiva `frankenphp`
+
+Per quanto riguarda le SAPI FPM e CLI, le variabili di ambiente sono esposte per impostazione predefinita nel superglobale `$_SERVER`.
+
+Il valore `S` della [direttiva PHP `variables_order`](https://www.php.net/manual/en/ini.core.php#ini.variables-order) è sempre equivalente a `ES` indipendentemente dal posizionamento di `E` altrove in questa direttiva.
+
+## Configurazione PHP
+
+Per caricare [file di configurazione PHP aggiuntivi](https://www.php.net/manual/en/configuration.file.php#configuration.file.scan),
+è possibile utilizzare la variabile di ambiente `PHP_INI_SCAN_DIR`.
+Quando impostato, PHP caricherà tutti i file con estensione `.ini` presenti nelle cartelle indicate.
+
+Puoi anche modificare la configurazione PHP utilizzando la direttiva `php_ini` in `Caddyfile`:
+
+```caddyfile
+{
+ frankenphp {
+ php_ini memory_limit 256M
+
+ # or
+
+ php_ini {
+ memory_limit 256M
+ max_execution_time 15
+ }
+ }
+}
+```
+
+### Disabilitare HTTPS
+
+Per impostazione predefinita, FrankenPHP abiliterà automaticamente HTTPS per tutti i nomi host, incluso `localhost`.
+Se si desidera disabilitare HTTPS (ad esempio in un ambiente di sviluppo), si può impostare la variabile di ambiente `SERVER_NAME` a `http://` o `:80`:
+
+In alternativa, è possibile utilizzare tutti gli altri metodi descritti nella [documentazione Caddy](https://caddyserver.com/docs/automatic-https#activation).
+
+Se si vuole utilizzare HTTPS con l'indirizzo IP `127.0.0.1` invece del nome host `localhost`, leggere la sezione [problemi noti](known-issues.md#using-https127001-with-docker).
+
+### Duplex completo (HTTP/1)
+
+Quando si utilizza HTTP/1.x, potrebbe essere opportuno abilitare la modalità full-duplex per consentire la scrittura di una risposta prima che l'intero body
+sia stato letto. (ad esempio: [Mercure](mercure.md), WebSocket, eventi inviati dal server, ecc.)
+
+Questa è una configurazione opt-in che deve essere aggiunta alle opzioni globali in `Caddyfile`:
+
+```caddyfile
+{
+ servers {
+ enable_full_duplex
+ }
+}
+```
+
+> [!CAUTION]
+>
+> L'abilitazione di questa opzione potrebbe causare un deadlock dei vecchi client HTTP/1.x che non supportano il full-duplex.
+> Questo può anche essere configurato utilizzando la configurazione dell'ambiente `CADDY_GLOBAL_OPTIONS`:
+
+```sh
+CADDY_GLOBAL_OPTIONS="servers {
+ enable_full_duplex
+}"
+```
+
+Puoi trovare ulteriori informazioni su questa impostazione nella [documentazione Caddy](https://caddyserver.com/docs/caddyfile/options#enable-full-duplex).
+
+## Abilita la modalità debug
+
+Quando si utilizza l'immagine Docker, impostare la variabile di ambiente `CADDY_GLOBAL_OPTIONS` su `debug` per abilitare la modalità debug:
+
+```console
+docker run -v $PWD:/app/public \
+ -e CADDY_GLOBAL_OPTIONS=debug \
+ -p 80:80 -p 443:443 -p 443:443/udp \
+ dunglas/frankenphp
+```
+
+## Completamento della shell
+
+FrankenPHP fornisce il supporto integrato per il completamento della shell per Bash, Zsh, Fish e PowerShell. Ciò abilita il completamento automatico per tutti i comandi (inclusi i comandi personalizzati come `php-server`, `php-cli` e `extension-init`) e i relativi flag.
+
+### Bah
+
+Per caricare i completamenti nella sessione di shell corrente:
+
+```console
+source <(frankenphp completion bash)
+```
+
+Per caricare i completamenti per ogni nuova sessione, eseguire:
+
+**Linux:**
+
+```console
+frankenphp completion bash > /usr/share/bash-completion/completions/frankenphp
+```
+
+**macOS:**
+
+```console
+frankenphp completion bash > $(brew --prefix)/share/bash-completion/completions/frankenphp
+```
+
+### Zsh
+
+Se il completamento della shell non è già abilitato nell'ambiente, andrà abilitato. È possibile eseguire quanto segue una volta:
+
+```console
+echo "autoload -U compinit; compinit" >> ~/.zshrc
+```
+
+Per caricare i completamenti per ogni sessione, eseguire una volta:
+
+```console
+frankenphp completion zsh > "${fpath[1]}/_frankenphp"
+```
+
+Sarà necessario avviare una nuova shell affinché questa configurazione abbia effetto.
+
+### Pescare
+
+Per caricare i completamenti nella sessione di shell corrente:
+
+```console
+frankenphp completion fish | source
+```
+
+Per caricare i completamenti per ogni nuova sessione, eseguire una volta:
+
+```console
+frankenphp completion fish > ~/.config/fish/completions/frankenphp.fish
+```
+
+### PowerShell
+
+Per caricare i completamenti nella sessione di shell corrente:
+
+```powershell
+frankenphp completion powershell | Out-String | Invoke-Expression
+```
+
+Per caricare i completamenti per ogni nuova sessione, eseguire una volta:
+
+```powershell
+frankenphp completion powershell | Out-File -FilePath (Join-Path (Split-Path $PROFILE) "frankenphp.ps1")
+Add-Content -Path $PROFILE -Value '. (Join-Path (Split-Path $PROFILE) "frankenphp.ps1")'
+```
+
+Sarà necessario avviare una nuova shell affinché questa configurazione abbia effetto.
diff --git a/docs/it/docker.md b/docs/it/docker.md
new file mode 100644
index 0000000000..7f908fa107
--- /dev/null
+++ b/docs/it/docker.md
@@ -0,0 +1,274 @@
+# Creazione di un'immagine Docker personalizzata
+
+Le [immagini Docker](https://hub.docker.com/r/dunglas/frankenphp) sono basate su [immagini PHP ufficiali](https://hub.docker.com/_/php/).
+Per le architetture più diffuse vengono fornite varianti Debian e Alpine Linux.
+Si consigliano le varianti Debian.
+
+Sono fornite varianti per PHP 8.2, 8.3, 8.4 e 8.5.
+
+I tag seguono questo schema: `dunglas/frankenphp:-php-`
+
+- `` e `` sono rispettivamente i numeri di versione di FrankenPHP e PHP, che vanno dalla versione maggiore (ad esempio `1`), minore (ad esempio `1.2`) alle versioni patch (ad esempio `1.2.3`).
+- `` è `trixie` (per Debian Trixie), `bookworm` (per Debian Bookworm) o `alpine` (per l'ultima versione stabile di Alpine).
+
+[Sfogliare i tag](https://hub.docker.com/r/dunglas/frankenphp/tags).
+
+## Come utilizzare le immagini Docker di FrankenPHP
+
+Creare un `Dockerfile` nel proprio progetto:
+
+```dockerfile
+FROM dunglas/frankenphp
+
+COPY . /app/public
+```
+
+Quindi, eseguire questi comandi per creare ed eseguire l'immagine Docker:
+
+```console
+docker build -t my-php-app .
+docker run -it --rm --name my-running-app my-php-app
+```
+
+## Come modificare la configurazione di FrankenPHP Docker
+
+Per comodità, [un `Caddyfile` predefinito](https://github.com/php/frankenphp/blob/main/caddy/frankenphp/Caddyfile) contenente
+le variabili di ambiente utili viene fornito nell'immagine.
+
+## Come installare altre estensioni PHP
+
+Lo script [`docker-php-extension-installer`](https://github.com/mlocati/docker-php-extension-installer) è fornito nell'immagine di base.
+Aggiungere ulteriori estensioni PHP è semplice:
+
+```dockerfile
+FROM dunglas/frankenphp
+
+# aggiungere eventuali altre esensioni qui:
+RUN install-php-extensions \
+ pdo_mysql \
+ gd \
+ intl \
+ zip \
+ opcache
+```
+
+## Come installare altri moduli Caddy
+
+FrankenPHP è basato su Caddy e tutti i [moduli Caddy](https://caddyserver.com/docs/modules/) possono essere utilizzati con FrankenPHP.
+
+Il modo più semplice per installare moduli Caddy personalizzati è utilizzare [xcaddy](https://github.com/caddyserver/xcaddy):
+
+```dockerfile
+FROM dunglas/frankenphp:builder AS builder
+
+# Copiare xcaddy nell'immagine
+COPY --from=caddy:builder /usr/bin/xcaddy /usr/bin/xcaddy
+
+# Occorre abilitare CGO per la build di FrankenPHP
+RUN CGO_ENABLED=1 \
+ XCADDY_SETCAP=1 \
+ XCADDY_GO_BUILD_FLAGS="-ldflags='-w -s' -tags=nobadger,nomysql,nopgx" \
+ CGO_CFLAGS=$(php-config --includes) \
+ CGO_LDFLAGS="$(php-config --ldflags) $(php-config --libs)" \
+ xcaddy build \
+ --output /usr/local/bin/frankenphp \
+ --with github.com/dunglas/frankenphp=./ \
+ --with github.com/dunglas/frankenphp/caddy=./caddy/ \
+ --with github.com/dunglas/caddy-cbrotli \
+ # Mercure e Vulcain sono inclusi nella build ufficiale, ma possono essere rimossi a piacimento
+ --with github.com/dunglas/mercure/caddy \
+ --with github.com/dunglas/vulcain/caddy
+ # Aggiungere eventuali altri moduli Caddy qui
+
+FROM dunglas/frankenphp AS runner
+
+# Sostituisce il binario ufficiale con quell contenente i moduli personalizzati
+COPY --from=builder /usr/local/bin/frankenphp /usr/local/bin/frankenphp
+```
+
+L'immagine `builder` fornita da FrankenPHP contiene una versione compilata di `libphp`.
+[Immagini builder](https://hub.docker.com/r/dunglas/frankenphp/tags?name=builder) sono fornite per tutte le versioni di FrankenPHP e PHP, sia per Debian sia per Alpine.
+
+> [!TIP]
+>
+> Se si usano Alpine Linux e Symfony,
+> potrebbe essere necessario [aumentare la dimensione dello stack predefinita](compile.md#using-xcaddy).
+
+## Abilitazione della modalità worker per impostazione predefinita
+
+Impostare la variabile d'ambiente `FRANKENPHP_CONFIG` per avviare FrankenPHP con uno script worker:
+
+```dockerfile
+FROM dunglas/frankenphp
+
+# ...
+
+ENV FRANKENPHP_CONFIG="worker ./public/index.php"
+```
+
+## Utilizzo di un volume in fase di sviluppo
+
+Per sviluppare facilmente con FrankenPHP, montare la cartella dell'host contenente il codice dell'applicazione come volume nel contenitore Docker:
+
+```console
+docker run -v $PWD:/app/public -p 80:80 -p 443:443 -p 443:443/udp --tty my-php-app
+```
+
+> [!TIP]
+>
+> L'opzione `--tty` consente di avere log leggibili invece dei log JSON.
+
+Con Docker Compose:
+
+```yaml
+# compose.yaml
+
+services:
+ php:
+ image: dunglas/frankenphp
+ # scommentare questa riga se si vuole un proprio Dockerfile
+ #build: .
+ # scommentare questa riga per eseguire in ambiente di produzione
+ # restart: always
+ ports:
+ - "80:80" # HTTP
+ - "443:443" # HTTPS
+ - "443:443/udp" # HTTP/3
+ volumes:
+ - ./:/app/public
+ - caddy_data:/data
+ - caddy_config:/config
+ # commentare questa riga in produzione, consente di avere log leggibili in dev
+ tty: true
+
+# Volumi necessari per certificati e configurazione di Caddy
+volumes:
+ caddy_data:
+ caddy_config:
+```
+
+## Esecuzione come utente non root
+
+FrankenPHP può essere eseguito come utente non root in Docker.
+
+Ecco un esempio di `Dockerfile` che esegue questa operazione:
+
+```dockerfile
+FROM dunglas/frankenphp
+
+ARG USER=appuser
+
+RUN <<-EOF
+ # Usare "adduser -D ${USER}" in distro basate su Alpine
+ useradd ${USER}
+ # Capacità aggiuntive di bind su porte 80 e 443
+ setcap CAP_NET_BIND_SERVICE=+eip /usr/local/bin/frankenphp
+ # Dà accesso in scrittura a /config/caddy e /data/caddy
+ chown -R ${USER}:${USER} /config/caddy /data/caddy
+EOF
+
+USER ${USER}
+```
+
+### Esecuzione senza capacità
+
+Anche quando viene eseguito senza root, FrankenPHP necessita della funzionalità `CAP_NET_BIND_SERVICE` per associare il
+server web su porte privilegiate (80 e 443).
+
+Espondendo FrankenPHP su una porta non privilegiata (1024 e successive), è possibile eseguire
+il server web come utente non root e senza la necessità di altre funzionalità:
+
+```dockerfile
+FROM dunglas/frankenphp
+
+ARG USER=appuser
+
+RUN <<-EOF
+ # Usare "adduser -D ${USER}" in distro basate su Alpine
+ useradd ${USER}
+ # Rimuove capacità predefinite
+ setcap -r /usr/local/bin/frankenphp
+ # Dà accesso in scrittura a /config/caddy e /data/caddy
+ chown -R ${USER}:${USER} /config/caddy /data/caddy
+EOF
+
+USER ${USER}
+```
+
+Successivamente, imposta la variabile di ambiente `SERVER_NAME` per utilizzare una porta non privilegiata.
+Esempio: `:8000`
+
+## Aggiornamenti dell'immagine Docker di FrankenPHP
+
+Le immagini Docker vengono create:
+
+- quando viene rilasciata una nuova versione
+- tutti i giorni alle 4:00 UTC, se sono disponibili nuove versioni delle immagini ufficiali di PHP
+
+## Rafforzamento delle immagini
+
+Per ridurre ulteriormente la superficie di attacco e le dimensioni delle immagini Docker di FrankenPHP, è anche possibile costruirle su
+[Google distroless](https://github.com/GoogleContainerTools/distroless) o su un'immagine
+[Docker rafforzata](https://www.docker.com/products/hardened-images).
+
+> [!WARNING]
+> Queste immagini di base minime non includono una shell o un gestore di pacchetti, il che rende il debug più difficile.
+> Sono quindi consigliate solo per la produzione, se la sicurezza è una priorità elevata.
+
+Quando si aggiungono estensioni PHP, sarà necessaria una fase di compilazione intermedia:
+
+```dockerfile
+FROM dunglas/frankenphp AS builder
+
+# Estensioni PHP aggiuntive
+RUN install-php-extensions pdo_mysql pdo_pgsql #...
+
+# Copia le librerie condivisie di frankenphp e tutte le estensioni installate in una posizione temporanea
+# You can also do this step manually by analyzing ldd output of frankenphp binary and each extension .so file
+RUN <<-EOF
+ apt-get update
+ apt-get install -y --no-install-recommends libtree
+ mkdir -p /tmp/libs
+ for target in $(which frankenphp) \
+ $(find "$(php -r 'echo ini_get("extension_dir");')" -maxdepth 2 -name "*.so"); do
+ libtree -pv "$target" 2>/dev/null | grep -oP '(?:── )\K/\S+(?= \[)' | while IFS= read -r lib; do
+ [ -f "$lib" ] && cp -n "$lib" /tmp/libs/
+ done
+ done
+EOF
+
+
+# Immagine di base Debian Distroless, assicurarsi che coincida con la versione di Debian del builder
+FROM gcr.io/distroless/base-debian13
+# Immagine Docker rafforzata alternativa
+# FROM dhi.io/debian:13
+
+COPY --from=builder /usr/local/bin/frankenphp /usr/local/bin/frankenphp
+COPY --from=builder /usr/local/lib/php/extensions /usr/local/lib/php/extensions
+COPY --from=builder /tmp/libs /usr/lib
+
+COPY --from=builder /usr/local/etc/php/conf.d /usr/local/etc/php/conf.d
+COPY --from=builder /usr/local/etc/php/php.ini-production /usr/local/etc/php/php.ini
+
+# Configurazione e dati devono essere scrivibili da tutti, anche su un filesystem in sola lettura
+ENV XDG_CONFIG_HOME=/config XDG_DATA_HOME=/data
+COPY --from=builder --chown=nonroot:nonroot /data /data
+COPY --from=builder --chown=nonroot:nonroot /config /config
+
+# Copia l'applicazione (mantenuta di proprietà di root) e Caddyfile
+COPY . /app
+COPY Caddyfile /etc/caddy/Caddyfile
+
+USER nonroot
+WORKDIR /app
+
+ENTRYPOINT ["/usr/local/bin/frankenphp", "run", "--config", "/etc/caddy/Caddyfile"]
+```
+
+## Versioni di sviluppo
+
+Le versioni di sviluppo sono disponibili su [`dunglas/frankenphp-dev`](https://hub.docker.com/repository/docker/dunglas/frankenphp-dev).
+Una nuova build viene attivata ogni volta che un commit viene inviato al ramo main del repository GitHub.
+
+I tag `latest*` puntano all'head del ramo `main`.
+Sono disponibili anche i tag nel formato `sha-`.
diff --git a/docs/it/early-hints.md b/docs/it/early-hints.md
new file mode 100644
index 0000000000..f3e7cc366d
--- /dev/null
+++ b/docs/it/early-hints.md
@@ -0,0 +1,21 @@
+# Early Hints
+
+FrankenPHP supporta nativamente il [codice di stato 103 Early Hints](https://developer.chrome.com/blog/early-hints/).
+Utilizzando Early Hints si può migliorare il tempo di caricamento delle pagine web del 30%.
+
+```php
+; rel=preload; as=style');
+headers_send(103);
+
+// qualcocsa di lento... 🤪
+
+echo <<<'HTML'
+
+Hello FrankenPHP
+
+HTML;
+```
+
+Gli Early Hints sono supportati sia dalla modalità normale sia da quella [worker](worker.md).
diff --git a/docs/it/embed.md b/docs/it/embed.md
new file mode 100644
index 0000000000..d0af270416
--- /dev/null
+++ b/docs/it/embed.md
@@ -0,0 +1,145 @@
+# App PHP come file binari autonomi
+
+FrankenPHP ha la capacità di incorporare il codice sorgente e le risorse delle applicazioni PHP in un binario statico e autonomo.
+
+Grazie a questa funzionalità, le applicazioni PHP possono essere distribuite come binari autonomi che includono l'applicazione stessa, l'interprete PHP e Caddy, un server web pronto per la produzione.
+
+Scopri di più su questa funzionalità [nella presentazione fatta da Kévin alla SymfonyCon 2023](https://dunglas.dev/2023/12/php-and-symfony-apps-as-standalone-binaries/).
+
+Per incorporare applicazioni Laravel, [leggi questa specifica voce della documentazione](laravel.md#laravel-apps-as-standalone-binaries).
+
+## Preparazione dell'app
+
+Prima di creare il file binario autonomo, assicurarsi che l'app sia pronta per l'embed.
+
+Ad esempio, probabilmente si vorrà:
+
+- Installare le dipendenze di produzione dell'app
+- Fare un dump dell'autoloader
+- Abilitare la modalità di produzione dell'applicazione (se presente)
+- Eliminare i file non necessari, come `.git` o i testm per ridurre la dimensione del file binario finale
+
+Ad esempio, per un'app Symfony, si può utilizzare i seguenti comandi:
+
+```console
+# Esporta il progetto per togliere .git/ e altri file
+mkdir $TMPDIR/my-prepared-app
+git archive HEAD | tar -x -C $TMPDIR/my-prepared-app
+cd $TMPDIR/my-prepared-app
+
+# Imposta le variabili d'ambiente adeguate
+echo APP_ENV=prod > .env.local
+echo APP_DEBUG=0 >> .env.local
+
+# Rimuove i test e altri file superflui, per salvare spazio
+# In altrenativa, aggiungere i percorsi all'attributo export-ignore dentro al file .gitattributes
+rm -Rf tests/
+
+# Installa le dipendenze
+composer install --ignore-platform-reqs --no-dev -a
+
+# Ottimizza .env
+composer dump-env prod
+```
+
+### Personalizzazione della configurazione
+
+Per personalizzare [la configurazione](config.md), si possono inserire un file `Caddyfile` e un file `php.ini`
+nella cartella principale dell'app per l'embed (`$TMPDIR/my-prepared-app` nell'esempio precedente).
+
+## Creazione di un binario Linux
+
+Il modo più semplice per creare un binario Linux è utilizzare il builder fornito, basato su Docker.
+
+1. Creare un file denominato `static-build.Dockerfile` nel repository dell'app:
+
+ ```dockerfile
+ # static-build.Dockerfile
+ FROM --platform=linux/amd64 dunglas/frankenphp:static-builder-gnu
+ # Se si vuole eseguire il binario su sistemi musl-libc, usare invece static-builder-musl
+
+ # Copia l'app
+ WORKDIR /go/src/app/dist/app
+ COPY . .
+
+ # Costruisce il binario statico
+ WORKDIR /go/src/app/
+ RUN EMBED=dist/app/ ./build-static.sh
+ ```
+
+ > [!CAUTION]
+ >
+> Alcuni file `.dockerignore` (ad esempio quello di [Symfony](https://github.com/dunglas/symfony-docker/blob/main/.dockerignore)
+> ignorabi la cartella `vendor/` e i file `.env`. Assicurarsi di modificare o rimuovere il file `.dockerignore` prima della build.
+
+2. Build:
+
+ ```console
+ docker build -t static-app -f static-build.Dockerfile .
+ ```
+
+3. Estrazione del file binario:
+
+ ```console
+ docker cp $(docker create --name static-app-tmp static-app):/go/src/app/dist/frankenphp-linux-x86_64 my-app ; docker rm static-app-tmp
+ ```
+
+Il file binario risultante è il file denominato `my-app` nella cartella corrente.
+
+## Creazione di un binario per altri sistemi operativi
+
+Se non si vuole usare Docker o si vuole creare un file binario macOS, usare lo script fornito:
+
+```console
+git clone https://github.com/php/frankenphp
+cd frankenphp
+EMBED=/path/to/your/app ./build-static.sh
+```
+
+Il file binario risultante è il file denominato `frankenphp--` nella cartella `dist/`.
+
+## Uso del binario
+
+Questo è tutto! Il file `my-app` (o `dist/frankenphp--` su altri sistemi operativi) contiene l'app autonoma!
+
+Per avviare l'esecuzione dell'app Web:
+
+```console
+./my-app php-server
+```
+
+Se l'app contiene uno [worker script](worker.md), avvia il worker con qualcosa come:
+
+```console
+./my-app php-server --worker public/index.php
+```
+
+Per abilitare HTTPS (viene creato automaticamente un certificato Let's Encrypt), HTTP/2 e HTTP/3, specificare il nome di dominio da usare:
+
+```console
+./my-app php-server --domain localhost
+```
+
+Si possono anche eseguire gli script CLI PHP inclusi nel binario:
+
+```console
+./my-app php-cli bin/console
+```
+
+## Estensioni PHP
+
+Per impostazione predefinita, lo script creerà le estensioni richieste dal file `composer.json` del progetto, se presente.
+Se il file `composer.json` non esiste, vengono create le estensioni predefinite, come documentato nella [voce sulle build statiche](static.md).
+
+Per personalizzare le estensioni, si può usare la variabile di ambiente `PHP_EXTENSIONS`.
+
+## Personalizzazione della build
+
+[Leggere la documentazione sulla build statica](static.md) per vedere come personalizzare il file binario (estensioni, versione PHP...).
+
+## Distribuire il binario
+
+Su Linux, il file binario creato viene compresso con [UPX](https://upx.github.io).
+
+Su Mac, per ridurre la dimensione del file prima di inviarlo, lo si può comprimere.
+Consigliamo di usare `xz`.
diff --git a/docs/it/extension-workers.md b/docs/it/extension-workers.md
new file mode 100644
index 0000000000..2251cbd60c
--- /dev/null
+++ b/docs/it/extension-workers.md
@@ -0,0 +1,176 @@
+# Extension worker
+
+Gli extension worker consentono all'[estensione FrankenPHP](https://frankenphp.dev/docs/extensions/) di gestire un pool dedicato di thread PHP per l'esecuzione di attività in background, la gestione di eventi asincroni o l'implementazione di protocolli personalizzati. Utile per sistemi di code, ascoltatori di eventi, pianificatori, ecc.
+
+## Registrare il worker
+
+### Registrazione statica
+
+Se non è necessario rendere il worker configurabile dall'utente (percorso di script fisso, numero fisso di thread), è possibile semplicemente registrare il worker nella funzione `init()`.
+
+```go
+// Registrazione statica
+package myextension
+
+import (
+ "github.com/dunglas/frankenphp"
+ "github.com/dunglas/frankenphp/caddy"
+)
+
+// Handle globale per comunicaer col pool dei worker
+var worker frankenphp.Workers
+
+func init() {
+ // Register the worker when the module is loaded.
+ worker = caddy.RegisterWorkers(
+ "my-internal-worker", // nome univoco
+ "worker.php", // Percorso dello script (relativo all'esecuzione o assoluto)
+ 2, // Conteggio fisso dei thread
+ // Hook opzionali del ciclo di vita
+ frankenphp.WithWorkerOnServerStartup(func() {
+ // Logica globale di setup...
+ }),
+ )
+}
+```
+
+### In un modulo Caddy (configurabile dall'utente)
+
+Se si vuole condividere l'estensione (come una coda generica o un ascoltatore di eventi), andrebbe inserita in un modulo Caddy. Ciò consente agli utenti di configurare il percorso dello script e il conteggio dei thread tramite `Caddyfile`. Ciò richiede l'implementazione dell'interfaccia `caddy.Provisioner` e l'analisi del Caddyfile ([vedi l'esempio del modulo Caddy frankenphp-queue](https://github.com/dunglas/frankenphp-queue/blob/main/caddy.go)).
+
+### In un'applicazione Go pura (embed)
+
+Se si usa l'[embed di FrankenPHP in un'applicazione Go standard senza caddy](https://pkg.go.dev/github.com/dunglas/frankenphp#example-ServeHTTP), si possono registrare i worker usando `frankenphp.WithExtensionWorkers` durante l'inizializzazione delle opzioni.
+
+## Interagire coi worker
+
+Una volta che il pool di worker è attivo, gli si possono inviare attività. Lo si può fare all'interno di [funzioni native esportate in PHP](https://frankenphp.dev/docs/extensions/#writing-the-extension) o da qualsiasi logica Go, come un cron, un ascoltatore di eventi (MQTT, Kafka) o qualsiasi altra goroutine.
+
+### Modalità headless: `SendMessage`
+
+Utilizzare `SendMessage` per passare i dati grezzi direttamente al worker. Questo è l'ideale per code o comandi semplici.
+
+#### Esempio di estensione della coda asincrona
+
+```go
+// Estensione FrankenPHP: invia messaggi a un worker tramite SendMessage
+// #include
+import "C"
+import (
+ "context"
+ "unsafe"
+ "github.com/dunglas/frankenphp"
+)
+
+//export_php:function my_queue_push(mixed $data): bool
+func my_queue_push(data *C.zval) bool {
+ // 1. Verifica che il worker sia pronto
+ if worker == nil {
+ return false
+ }
+
+ // 2. Invia al worker in backjground
+ _, err := worker.SendMessage(
+ context.Background(), // Contesto Go standard
+ unsafe.Pointer(data), // Dati da passare al worker
+ nil, // http.ResponseWriter (facoltativo)
+ )
+
+ return err == nil
+}
+```
+
+### Emulazione HTTP: `SendRequest`
+
+Utilizzare `SendRequest` se l'estensione deve richiamare uno script PHP che prevede un ambiente Web standard (popolando `$_SERVER`, `$_GET`, ecc.).
+
+```go
+// Estensione FrankenPHP: invoca uno script PHP con worker tramite SendRequest (emulazione HTTP)
+// #include
+import "C"
+import (
+ "net/http"
+ "net/http/httptest"
+ "unsafe"
+ "github.com/dunglas/frankenphp"
+)
+
+//export_php:function my_worker_http_request(string $path): string
+func my_worker_http_request(path *C.zend_string) unsafe.Pointer {
+ // 1. Prepara request e recorder
+ url := frankenphp.GoString(unsafe.Pointer(path))
+ req, _ := http.NewRequest("GET", url, http.NoBody)
+ rr := httptest.NewRecorder()
+
+ // 2. Invia al worker
+ if err := worker.SendRequest(rr, req); err != nil {
+ return nil
+ }
+
+ // 3. Restituisce la risposta catturata
+ return frankenphp.PHPString(rr.Body.String(), false)
+}
+```
+
+## Script worker
+
+Lo script worker PHP viene eseguito in un ciclo e può gestire sia messaggi non elaborati sia richieste HTTP.
+
+```php
+ [!TIP]
+> Per capire come scrivere le estensioni in Go da zero, leggere la sezione di implementazione manuale di seguito, che mostra come scrivere un'estensione PHP in Go senza utilizzare il generatore.
+
+Tieni presente che questo strumento **non è un generatore di estensioni completo**. È pensato per aiutarti a scrivere semplici estensioni in Go, ma non fornisce le funzionalità più avanzate delle estensioni PHP. Se hai bisogno di scrivere un'estensione più **complessa e ottimizzata**, potresti dover scrivere del codice C o utilizzare direttamente CGO.
+
+### Prerequisiti
+
+Come spiegato anche nella sezione di implementazione manuale di seguito, è necessario [recuperare i sorgenti PHP](https://www.php.net/downloads.php) e creare un nuovo modulo Go.
+
+#### Creare un nuovo modulo e ottieni i sorgenti PHP
+
+Il primo passo per scrivere un'estensione PHP in Go è creare un nuovo modulo Go. È possibile utilizzare il seguente comando per questo:
+
+```console
+go mod init example.com/example
+```
+
+Il secondo passaggio consiste nel [recuperare i sorgenti PHP](https://www.php.net/downloads.php) per i passaggi successivi. Successivamente, basta decomprimerli nella cartella desiderata, non nel modulo Go:
+
+```console
+tar xf php-*
+```
+
+### Scrivere l'estensione
+
+Ora tutto è impostato per scrivere una funzione nativa in Go. Creare un nuovo file denominato `stringext.go`. La nostra prima funzione prenderà una stringa come argomento, il numero di volte per ripeterla, un booleano per indicare se invertire la stringa e restituirà la stringa risultante. Qualcosa come:
+
+```go
+// stringext.go
+package example
+
+// #include
+import "C"
+import (
+ "strings"
+ "unsafe"
+
+ "github.com/dunglas/frankenphp"
+)
+
+//export_php:function repeat_this(string $str, int $count, bool $reverse): string
+func repeat_this(s *C.zend_string, count int64, reverse bool) unsafe.Pointer {
+ str := frankenphp.GoString(unsafe.Pointer(s))
+
+ result := strings.Repeat(str, int(count))
+ if reverse {
+ runes := []rune(result)
+ for i, j := 0, len(runes)-1; i < j; i, j = i+1, j-1 {
+ runes[i], runes[j] = runes[j], runes[i]
+ }
+ result = string(runes)
+ }
+
+ return frankenphp.PHPString(result, false)
+}
+```
+
+Ci sono due cose importanti da notare:
+
+- Un commento direttiva `//export_php:function` definisce la firma della funzione in PHP. In questo modo il generatore sa come generare la funzione PHP con i parametri e il tipo di ritorno corretti.
+- La funzione deve restituire un `unsafe.Pointer`. FrankenPHP fornisce un'API per gestire il type juggliing tra C e Go.
+
+Mentre il primo punto parla da solo, il secondo potrebbe essere più difficile da comprendere. Approfondiremo meglio il type juggling più avanti.
+
+### Generazione dell'estensione
+
+È qui che avviene la magia e ora è possibile generare l'estensione. È possibile eseguire il generatore con il seguente comando:
+
+```console
+GEN_STUB_SCRIPT=php-src/build/gen_stub.php frankenphp extension-init my_extension.go
+```
+
+> [!NOTE]
+> Non dimenticare di impostare la variabile d'ambiente `GEN_STUB_SCRIPT` sul percorso del file `gen_stub.php` nei sorgenti PHP scaricati in precedenza. Questo è lo stesso script `gen_stub.php` menzionato nella sezione di implementazione manuale.
+
+Se tutto è andato bene, la cartella del progetto dovrebbe contenere i seguenti file per l'estensione:
+
+- **`my_extension.go`** - Il file sorgente originale (rimane invariato)
+- **`my_extension_generated.go`** - File generato con wrapper CGO che chiamano le funzioni personalizzate
+- **`my_extension.stub.php`** - File stub PHP per il completamento automatico dell'IDE
+- **`my_extension_arginfo.h`** - Informazioni sull'argomento PHP
+- **`my_extension.h`** - File di intestazione C
+- **`my_extension.c`** - File di implementazione C
+- **`README.md`** - Documentazione
+
+> [!IMPORTANT]
+> **Il file sorgente (`my_extension.go`) non viene mai modificato.** Il generatore crea un file `_generated.go` separato, contenente wrapper CGO, che chiamano le funzioni originali. Ciò significa che si può controllare in sicurezza la versione del file sorgente senza preoccuparsi che il codice generato possa alterarlo.
+
+### Integrazione dell'estensione generata in FrankenPHP
+
+La nostra estensione è ora pronta per essere compilata e integrata in FrankenPHP. Per fare ciò, fare riferimento alla [documentazione di compilazione] di FrankenPHP(compile.md) per sapere come compilare FrankenPHP. Aggiungi il modulo utilizzando il flag `--with`, che punta al percorso del modulo:
+
+```console
+CGO_ENABLED=1 \
+XCADDY_GO_BUILD_FLAGS="-ldflags='-w -s' -tags=nobadger,nomysql,nopgx" \
+CGO_CFLAGS=$(php-config --includes) \
+CGO_LDFLAGS="$(php-config --ldflags) $(php-config --libs)" \
+xcaddy build \
+ --output frankenphp \
+ --with github.com/my-account/my-module/build
+```
+
+Si noti il puntamento alla sottocartella `/build`, creata durante il passaggio di generazione. Tuttavia, non è obbligatorio: si possono anche copiare i file generati nella cartella del modulo e puntarvi direttamente.
+
+### Test dell'estensione generata
+
+Si può usare un file PHP per testare le funzioni e le classi che appena create. Ad esempio, creare un file `index.php` con il seguente contenuto:
+
+```php
+process('Hello World', StringProcessor::MODE_LOWERCASE); // "hello world"
+echo $processor->process('Hello World', StringProcessor::MODE_UPPERCASE); // "HELLO WORLD"
+```
+
+Una volta integrata l'estensione in FrankenPHP, come mostrato nella sezione precedente, si può eseguire questo file di prova con `./frankenphp php-server` e l'estensione dovrebbe essere funzionante.
+
+### Type juggling
+
+Mentre alcuni tipi di variabili hanno la stessa rappresentazione della memoria tra C/PHP e Go, altri tipi richiedono un po' di logica per essere utilizzati direttamente. Questa è forse la parte più difficile quando si tratta di scrivere estensioni, perché richiede la comprensione di Zend Engine e di come le variabili vengono archiviate internamente in PHP.
+Questa tabella riassume il necessario:
+
+| Tipo PHP | Tipo Go | Conversione diretta | Helper C -> Go | Helper Go -> C | Supporto per i metodi di classe |
+| ------------------ | ----------------------- | ----------------- | --------------------------------- | ---------------------------------- | --------------------- |
+| `int` | `int64` | ✅ | - | - | ✅ |
+| `?int` | `*int64` | ✅ | - | - | ✅ |
+| `float` | `float64` | ✅ | - | - | ✅ |
+| `?float` | `*float64` | ✅ | - | - | ✅ |
+| `bool` | `bool` | ✅ | - | - | ✅ |
+| `?bool` | `*bool` | ✅ | - | - | ✅ |
+| `string`/`?string` | `*C.zend_string` | ❌| `frankenphp.GoString()` | `frankenphp.PHPString()` | ✅ |
+| `array` | `frankenphp.AssociativeArray` | ❌| `frankenphp.GoAssociativeArray()` | `frankenphp.PHPAssociativeArray()` | ✅ |
+| `array` | `map[string]any` | ❌| `frankenphp.GoMap()` | `frankenphp.PHPMap()` | ✅ |
+| `array` | `[]any` | ❌| `frankenphp.GoPackedArray()` | `frankenphp.PHPPackedArray()` | ✅ |
+| `mixed` | `any` | ❌| `GoValue()` | `PHPValue()` | ❌|
+| `callable` | `*C.zval` | ❌| - | frankenphp.CallPHPCallable() | ❌|
+| `object` | `struct` | ❌| _Non ancora implementato_ | _Non ancora implementato_ | ❌|
+
+> [!NOTE]
+>
+> Questa tabella non è ancora esaustiva e verrà completata man mano che l'API dei tipi FrankenPHP diventerà più completa.
+>
+> Per i metodi di classe, in particolare, sono attualmente supportati i tipi primitivi e gli array. Gli oggetti non possono ancora essere utilizzati come parametri di metodo o tipi di ritorno.
+
+Facendo riferimento allo snippet di codice della sezione precedente, si può vedere che gli helper vengono utilizzati per convertire il primo parametro e il valore restituito. Non è necessario convertire il secondo e il terzo parametro della nostra funzione `repeat_this()`, poiché la rappresentazione in memoria dei tipi sottostanti è la stessa sia per C sia per Go.
+
+#### Lavorare con gli array
+
+FrankenPHP fornisce supporto nativo per gli array PHP tramite `frankenphp.AssociativeArray` o conversione diretta per map e slice.
+
+`AssociativeArray` rappresenta una [mappa hash](https://en.wikipedia.org/wiki/Hash_table) composta da un campo `Map: map[string]any` e un campo `Order: []string` opzionale (a differenza degli "array associativi" PHP, le mappe Go non sono ordinate).
+
+Se l'ordine o l'associazione non sono necessari, è anche possibile convertire direttamente in una porzione `[]any` o in una mappa non ordinata `map[string]any`.
+
+**Creazione e manipolazione di array in Go:**
+
+```go
+// Conversione tra array PHP e map/slice Go
+package example
+
+// #include
+import "C"
+import (
+ "unsafe"
+
+ "github.com/dunglas/frankenphp"
+)
+
+// export_php:function process_data_ordered(array $input): array
+func process_data_ordered_map(arr *C.zend_array) unsafe.Pointer {
+ // Converte un array associativo PHP in Go, conservando l'ordinamento
+ associativeArray, err := frankenphp.GoAssociativeArray[any](unsafe.Pointer(arr))
+ if err != nil {
+ // gestione dell'errore
+ }
+
+ // cicla le voci in ordine
+ for _, key := range associativeArray.Order {
+ value, _ = associativeArray.Map[key]
+ // fare qualcosa con key e value
+ }
+
+ // restituisce un array ordinato
+ // se 'Order' non è vuoto, saranno rispettate solo le coppie chiave/valore in 'Order'
+ return frankenphp.PHPAssociativeArray[string](frankenphp.AssociativeArray[string]{
+ Map: map[string]string{
+ "key1": "value1",
+ "key2": "value2",
+ },
+ Order: []string{"key1", "key2"},
+ })
+}
+
+// export_php:function process_data_unordered(array $input): array
+func process_data_unordered_map(arr *C.zend_array) unsafe.Pointer {
+ // Converte array associativi PHP in GO, senza conservare l'ordinamento
+ // tralasciare l'ordinamento aumenta le prestazioni
+ goMap, err := frankenphp.GoMap[any](unsafe.Pointer(arr))
+ if err != nil {
+ // gestione dell'errore
+ }
+
+ // cicla le voci in ordine sparso
+ for key, value := range goMap {
+ // fare qualcosa con key e value
+ }
+
+ // restituisce un array non ordinato
+ return frankenphp.PHPMap(map[string]string {
+ "key1": "value1",
+ "key2": "value2",
+ })
+}
+
+// export_php:function process_data_packed(array $input): array
+func process_data_packed(arr *C.zend_array) unsafe.Pointer {
+ // Converte array compatti PHP in Go
+ goSlice, err := frankenphp.GoPackedArray(unsafe.Pointer(arr))
+ if err != nil {
+ // gestione dell'errore
+ }
+
+ // cicla le voci in ordine
+ for index, value := range goSlice {
+ // fare qualcosa con key e value
+ }
+
+ // restituisce un array compatto (senza "buchi")
+ return frankenphp.PHPPackedArray([]string{"value1", "value2", "value3"})
+}
+```
+
+**Caratteristiche principali della conversione di array:**
+
+- **Coppie chiave-valore ordinate** - Opzione per mantenere l'ordine dell'array associativo
+- **Ottimizzato per più casi** - Opzione per abbandonare l'ordine per prestazioni migliori o convertirlo direttamente in una sezione
+- **Rilevamento automatico di liste** - Durante la conversione in PHP, rileva automaticamente se l'array deve essere un elenco compresso o una mappa hash
+- **Array annidati** - Gli array possono essere annidati e convertiranno automaticamente tutti i tipi supportati (`int64`, `float64`, `string`, `bool`, `nil`, `AssociativeArray`, `map[string]any`, `[]any`)
+- **Gli oggetti non sono supportati** - Attualmente, solo i tipi scalari e gli array possono essere utilizzati come valori. Fornire un oggetto risulterà in un valore `null` nell'array PHP.
+
+##### Metodi disponibili: compresso e associativo
+
+- `frankenphp.PHPAssociativeArray(arr frankenphp.AssociativeArray) unsafe.Pointer` - Converti in un array PHP ordinato con coppie chiave-valore
+- `frankenphp.PHPMap(arr map[string]any) unsafe.Pointer` - Converte una mappa in un array PHP non ordinato con coppie chiave-valore
+- `frankenphp.PHPPackedArray(slice []any) unsafe.Pointer` - Converte una sezione in un array compresso PHP con solo valori indicizzati
+- `frankenphp.GoAssociativeArray(arr unsafe.Pointer, ordered bool) frankenphp.AssociativeArray` - Converte un array PHP in un Go ordinato `AssociativeArray` (mappa con ordine)
+- `frankenphp.GoMap(arr unsafe.Pointer) map[string]any` - Converte un array PHP in una mappa Go non ordinata
+- `frankenphp.GoPackedArray(arr unsafe.Pointer) []any` - Converte un array PHP in una sezione Go
+- `frankenphp.IsPacked(zval *C.zend_array) bool` - Controlla se un array PHP è compresso (solo indicizzato) o associativo (coppie chiave-valore)
+
+### Lavorare con callable
+
+FrankenPHP fornisce un modo per lavorare con callablePHP utilizzando l'helper `frankenphp.CallPHPCallable`. Ciò ti consente di chiamare funzioni o metodi PHP dal codice Go.
+
+Per dimostrarlo, creiamo la nostra funzione `array_map()` che accetta un callable e un array, applica il richiamabile a ciascun elemento dell'array e restituisce un nuovo array con i risultati:
+
+```go
+// Chiamando un callable PHP da una funzione estensione definita in Go
+// export_php:function my_array_map(array $data, callable $callback): array
+func my_array_map(arr *C.zend_array, callback *C.zval) unsafe.Pointer {
+ goSlice, err := frankenphp.GoPackedArray[any](unsafe.Pointer(arr))
+ if err != nil {
+ panic(err)
+ }
+
+ result := make([]any, len(goSlice))
+
+ for index, value := range goSlice {
+ result[index] = frankenphp.CallPHPCallable(unsafe.Pointer(callback), []interface{}{value})
+ }
+
+ return frankenphp.PHPPackedArray(result)
+}
+```
+
+Si noti come utilizziamo `frankenphp.CallPHPCallable()` per chiamare il callable PHP passato come parametro. Questa funzione accetta un puntatore al richiamabile e un array di argomenti e restituisce il risultato dell'esecuzione del callable. Si possono usare tutte le sintassi per i callable:
+
+```php
+name` non funziona)
+- **Interfaccia solo con metodi** - Tutte le interazioni devono passare attraverso i metodi definiti dall'utente
+- **Migliore incapsulamento** - La struttura dei dati interni è completamente controllata dal codice Go
+- **Sicurezza dei tipi** - Nessun rischio che il codice PHP corrompa lo stato interno con tipi errati
+- **API più pulita**: obbliga a progettare un'interfaccia pubblica adeguata
+
+Questo approccio fornisce un migliore incapsulamento e impedisce al codice PHP di corrompere accidentalmente lo stato interno degli oggetti Go. Tutte le interazioni con l'oggetto devono passare attraverso i metodi definiti esplicitamente.
+
+#### Aggiunta di metodi alle classi
+
+Poiché le proprietà non sono direttamente accessibili, **è necessario definire metodi** per interagire con le classi opache. Utilizzare la direttiva `//export_php:method` per definire il comportamento:
+
+```go
+// Definire dei metodi su una class PHP in Go
+package example
+
+// #include
+import "C"
+import (
+ "unsafe"
+
+ "github.com/dunglas/frankenphp"
+)
+
+//export_php:class User
+type UserStruct struct {
+ Name string
+ Age int
+}
+
+//export_php:method User::getName(): string
+func (us *UserStruct) GetUserName() unsafe.Pointer {
+ return frankenphp.PHPString(us.Name, false)
+}
+
+//export_php:method User::setAge(int $age): void
+func (us *UserStruct) SetUserAge(age int64) {
+ us.Age = int(age)
+}
+
+//export_php:method User::getAge(): int
+func (us *UserStruct) GetUserAge() int64 {
+ return int64(us.Age)
+}
+
+//export_php:method User::setNamePrefix(string $prefix = "User"): void
+func (us *UserStruct) SetNamePrefix(prefix *C.zend_string) {
+ us.Name = frankenphp.GoString(unsafe.Pointer(prefix)) + ": " + us.Name
+}
+```
+
+#### Parametri nullabili
+
+Il generatore supporta parametri nullabili utilizzando il prefisso `?` nelle firme PHP. Quando un parametro è nullabile, diventa un puntatore nella funzione Go, permettendo di verificare se il valore era `null` in PHP:
+
+```go
+// Gestione di parametri nullabili in PHP in un metodo Go
+package example
+
+// #include
+import "C"
+import (
+ "unsafe"
+
+ "github.com/dunglas/frankenphp"
+)
+
+//export_php:method User::updateInfo(?string $name, ?int $age, ?bool $active): void
+func (us *UserStruct) UpdateInfo(name *C.zend_string, age *int64, active *bool) {
+ // Controlla se name sia non nullo
+ if name != nil {
+ us.Name = frankenphp.GoString(unsafe.Pointer(name))
+ }
+
+ // Controlla se age sia non nullo
+ if age != nil {
+ us.Age = int(*age)
+ }
+
+ // Controlla se active sia non nullo
+ if active != nil {
+ us.Active = *active
+ }
+}
+```
+
+**Punti chiave sui parametri nullabili:**
+
+- **Tipi primitivi nullabili** (`?int`, `?float`, `?bool`) diventano puntatori (`*int64`, `*float64`, `*bool`) in Go
+- Le **stringhe nullabili** (`?string`) rimangono come `*C.zend_string` ma possono essere `nil`
+- **Verifica di `nil`** prima di dereferenziare i valori del puntatore
+- **PHP `null` diventa Go `nil`** - quando PHP passa `null`, la funzione Go riceve un puntatore `nil`
+
+> [!WARNING]
+>
+> Attualmente, i metodi delle classi presentano le seguenti limitazioni. **Gli oggetti non sono supportati** come tipi di parametri o tipi restituiti. **Gli array sono completamente supportati** sia per i parametri sia per i tipi restituiti. Tipi supportati: `string`, `int`, `float`, `bool`, `array` e `void` (per il tipo restituito). **I tipi di parametri Nullable sono completamente supportati** per tutti i tipi scalari (`?string`, `?int`, `?float`, `?bool`).
+
+Dopo aver generato l'estensione, sarà consentito utilizzare la classe e i suoi metodi in PHP. Si tenga presente che **non si può accedere direttamente alle proprietà**:
+
+```php
+setAge(25);
+echo $user->getName(); // Output: (vuoto, valore predefinito)
+echo $user->getAge(); // Output: 25
+$user->setNamePrefix("Employee");
+
+// ✅ Anche questo funziona, ha parametri nullabili
+$user->updateInfo("John", 30, true); // Tutti i parametri forniti
+$user->updateInfo("Jane", null, false); // Age è null
+$user->updateInfo(null, 25, null); // Name ed active sono null
+
+// ❌ NON funziona, cerca di accedere direttamente alle proprietà
+// echo $user->name; // Error: Cannot access private property
+// $user->age = 30; // Error: Cannot access private property
+```
+
+Questa progettazione garantisce che il codice Go abbia il controllo completo sul modo in cui si accede e si modifica lo stato dell'oggetto, fornendo un migliore incapsulamento e indipendenza dai tipi.
+
+### Dichiarare costanti
+
+Il generatore supporta l'esportazione di costanti Go in PHP utilizzando due direttive: `//export_php:const` per costanti globali e `//export_php:classconst` per costanti di classe. Ciò ti consente di condividere valori di configurazione, codici di stato e altre costanti tra Go e il codice PHP.
+
+#### Costanti globali
+
+Utilizzare la direttiva `//export_php:const` per creare costanti PHP globali:
+
+```go
+// Esportare costanti globali PHP da Go
+package example
+
+//export_php:const
+const MAX_CONNECTIONS = 100
+
+//export_php:const
+const API_VERSION = "1.2.3"
+
+//export_php:const
+const (
+ STATUS_OK = iota
+ STATUS_ERROR
+)
+```
+
+> [!NOTE]
+>
+> Le costanti PHP prenderanno il nome della costante Go, quindi è consigliabile utilizzare le lettere maiuscole.
+
+#### Costanti di classe
+
+Utilizzare la direttiva `//export_php:classconst ClassName` per creare costanti che appartengono a una specifica classe PHP:
+
+```go
+// Esportare costanti di classe PHP da Go
+package example
+
+//export_php:classconst User
+const STATUS_ACTIVE = 1
+
+//export_php:classconst User
+const STATUS_INACTIVE = 0
+
+//export_php:classconst User
+const ROLE_ADMIN = "admin"
+
+//export_php:classconst Order
+const (
+ STATE_PENDING = iota
+ STATE_PROCESSING
+ STATE_COMPLETED
+)
+```
+
+> [!NOTE]
+>
+> Proprio come le costanti globali, le costanti di classe prenderanno il nome della costante Go.
+
+Le costanti della classe sono accessibili utilizzando l'ambito del nome della classe in PHP:
+
+```php
+
+import "C"
+import (
+ "strings"
+ "unsafe"
+
+ "github.com/dunglas/frankenphp"
+)
+
+//export_php:const
+const STR_REVERSE = iota
+
+//export_php:const
+const STR_NORMAL = iota
+
+//export_php:classconst StringProcessor
+const MODE_LOWERCASE = 1
+
+//export_php:classconst StringProcessor
+const MODE_UPPERCASE = 2
+
+//export_php:function repeat_this(string $str, int $count, int $mode): string
+func repeat_this(s *C.zend_string, count int64, mode int) unsafe.Pointer {
+ str := frankenphp.GoString(unsafe.Pointer(s))
+
+ result := strings.Repeat(str, int(count))
+ if mode == STR_REVERSE {
+ // reverse the string
+ }
+
+ if mode == STR_NORMAL {
+ // no-op, just to showcase the constant
+ }
+
+ return frankenphp.PHPString(result, false)
+}
+
+//export_php:class StringProcessor
+type StringProcessorStruct struct {
+ // internal fields
+}
+
+//export_php:method StringProcessor::process(string $input, int $mode): string
+func (sp *StringProcessorStruct) Process(input *C.zend_string, mode int64) unsafe.Pointer {
+ str := frankenphp.GoString(unsafe.Pointer(input))
+
+ switch mode {
+ case MODE_LOWERCASE:
+ str = strings.ToLower(str)
+ case MODE_UPPERCASE:
+ str = strings.ToUpper(str)
+ }
+
+ return frankenphp.PHPString(str, false)
+}
+```
+
+### Uso dei namespace
+
+Il generatore supporta l'organizzazione delle funzioni, delle classi e delle costanti dell'estensione PHP in un namespace, utilizzando la direttiva `//export_php:namespace`. Ciò aiuta a evitare conflitti di denominazione e fornisce una migliore organizzazione per l'API dell'estensione.
+
+#### Dichiarare un namespace
+
+Utilizzare la direttiva `//export_php:namespace` nella parte superiore del file Go per mettere tutti i simboli esportati in un namespace specifico:
+
+```go
+// Mette i simboli esportati in namespace PHP
+//export_php:namespace My\Extension
+package example
+
+import (
+ "unsafe"
+
+ "github.com/dunglas/frankenphp"
+)
+
+//export_php:function hello(): string
+func hello() string {
+ return "Hello from My\\Extension namespace!"
+}
+
+//export_php:class User
+type UserStruct struct {
+ // internal fields
+}
+
+//export_php:method User::getName(): string
+func (u *UserStruct) GetName() unsafe.Pointer {
+ return frankenphp.PHPString("John Doe", false)
+}
+
+//export_php:const
+const STATUS_ACTIVE = 1
+```
+
+#### Utilizzo dell'estensione con namespace in PHP
+
+Quando viene dichiarato un namespace, tutte le funzioni, classi e costanti vengono inserite sotto quel namespace in PHP:
+
+```php
+getName(); // "John Doe"
+
+echo My\Extension\STATUS_ACTIVE; // 1
+```
+
+#### Note importanti
+
+- È consentita solo **una** direttiva namespace per file. Se vengono trovate più direttive namespace, il generatore restituirà un errore.
+- Il namespace si applica a **tutti** i simboli esportati nel file: funzioni, classi, metodi e costanti.
+- I namespace seguono le convenzioni dei namespace PHP con le barre rovesciate (`\`) come separatori.
+- Se non viene dichiarato alcun namespace, i simboli vengono esportati nel namespace globale, come al solito.
+
+## Implementazione manuale
+
+Se si vuole capire come funzionano le estensioni o si ha bisogno del pieno controllo sull'estensione, le si può scriverle manualmente. Questo approccio offre il controllo completo ma richiede più codice standard.
+
+### Funzione di base
+
+Vedremo come scrivere una semplice estensione PHP in Go che definisce una nuova funzione nativa. Questa funzione verrà chiamata da PHP e attiverà una goroutine che registra un messaggio nei log di Caddy. Questa funzione non accetta alcun parametro e non restituisce nulla.
+
+#### Definire la funzione Go
+
+Nel modulo, va definita una nuova funzione nativa che verrà chiamata da PHP. Per farlo, creare un file con il nome desiderato, ad esempio `extension.go`, e aggiungere il seguente codice:
+
+```go
+// extension.go
+package example
+
+// #include "extension.h"
+import "C"
+import (
+ "log/slog"
+ "unsafe"
+
+ "github.com/dunglas/frankenphp"
+)
+
+func init() {
+ frankenphp.RegisterExtension(unsafe.Pointer(&C.ext_module_entry))
+}
+
+//export go_print_something
+func go_print_something() {
+ go func() {
+ slog.Info("Hello from a goroutine!")
+ }()
+}
+```
+
+La funzione `frankenphp.RegisterExtension()` semplifica il processo di registrazione dell'estensione gestendo la logica di registrazione PHP interna. La funzione `go_print_something` utilizza la direttiva `//export` per indicare che sarà accessibile nel codice C che scriveremo, grazie a CGO.
+
+In questo esempio, la nostra nuova funzione attiverà una goroutine che registra un messaggio nei log di Caddy.
+
+#### Definire la funzione PHP
+
+Per consentire a PHP di chiamare la nostra funzione, dobbiamo definire una funzione PHP corrispondente. Per questo creeremo un file stub, ad esempio `extension.stub.php`, che conterrà il seguente codice:
+
+```php
+
+
+extern zend_module_entry ext_module_entry;
+
+#endif
+```
+
+Successivamente, creare un file denominato `extension.c` che eseguirà i seguenti passaggi:
+
+- Includere header PHP;
+- Dichiarare la nostra nuova funzione PHP nativa `go_print()`;
+- Dichiarare i metadati dell'estensione.
+
+Iniziamo includendo gli header richiesti:
+
+```c
+// extension.c
+#include
+#include "extension.h"
+#include "extension_arginfo.h"
+
+// Contains symbols exported by Go
+#include "_cgo_export.h"
+```
+
+Definiamo quindi la nostra funzione PHP come una funzione del linguaggio nativo:
+
+```c
+PHP_FUNCTION(go_print)
+{
+ ZEND_PARSE_PARAMETERS_NONE();
+
+ go_print_something();
+}
+
+zend_module_entry ext_module_entry = {
+ STANDARD_MODULE_HEADER,
+ "ext_go",
+ ext_functions, /* Functions */
+ NULL, /* MINIT */
+ NULL, /* MSHUTDOWN */
+ NULL, /* RINIT */
+ NULL, /* RSHUTDOWN */
+ NULL, /* MINFO */
+ "0.1.1",
+ STANDARD_MODULE_PROPERTIES
+};
+```
+
+In questo caso, la nostra funzione non accetta parametri e non restituisce nulla. Chiama semplicemente la funzione Go definita in precedenza, esportata utilizzando la direttiva `//export`.
+
+Infine, definiamo i metadati dell'estensione in una struttura `zend_module_entry`, come nome, versione e proprietà. Queste informazioni sono necessarie affinché PHP riconosca e carichi la nostra estensione. Tieni presente che `ext_functions` è un array di puntatori alle funzioni PHP che abbiamo definito ed è stato generato automaticamente dallo script `gen_stub.php` nel file `extension_arginfo.h`.
+
+La registrazione dell'estensione viene gestita automaticamente dalla funzione `RegisterExtension()` di FrankenPHP che chiamiamo nel nostro codice Go.
+
+### Utilizzo avanzato
+
+Ora che sappiamo come creare un'estensione PHP di base in Go, rendiamo più complesso il nostro esempio. Creeremo ora una funzione PHP che accetta una stringa come parametro e restituisce la sua versione in maiuscolo.
+
+#### Definire lo stub della funzione PHP
+
+Per definire la nuova funzione PHP, modificheremo il nostro file `extension.stub.php` per includere la nuova firma della funzione:
+
+```php
+ [!TIP]
+> Non trascurare la documentazione delle funzioni! È probabile che gli stub delle estensioni saranno condivisi con altri sviluppatori per documentare come utilizzare l'estensione e quali funzionalità sono disponibili.
+
+Rigenerando il file stub con lo script `gen_stub.php`, il file `extension_arginfo.h` dovrebbe assomigliare a questo:
+
+```c
+// extension_arginfo.h (generated)
+ZEND_BEGIN_ARG_WITH_RETURN_TYPE_INFO_EX(arginfo_go_upper, 0, 1, IS_STRING, 0)
+ ZEND_ARG_TYPE_INFO(0, string, IS_STRING, 0)
+ZEND_END_ARG_INFO()
+
+ZEND_FUNCTION(go_upper);
+
+static const zend_function_entry ext_functions[] = {
+ ZEND_FE(go_upper, arginfo_go_upper)
+ ZEND_FE_END
+};
+```
+
+Possiamo vedere che la funzione `go_upper` è definita con un parametro di tipo `string` e un tipo restituito di `string`.
+
+#### Type juggling tra Go e PHP/C
+
+La funzione Go non può accettare direttamente una stringa PHP come parametro. È necessario convertirlo in una stringa Go. Fortunatamente, FrankenPHP fornisce funzioni di supporto per gestire la conversione tra stringhe PHP e stringhe Go, simili a quanto visto nell'approccio del generatore.
+
+Il file header rimane semplice:
+
+```c
+// extension.h
+#ifndef _EXTENSION_H
+#define _EXTENSION_H
+
+#include
+
+extern zend_module_entry ext_module_entry;
+
+#endif
+```
+
+Ora possiamo scrivere il bridge tra Go e C nel nostro file `extension.c`. Passeremo la stringa PHP direttamente alla nostra funzione Go:
+
+```c
+PHP_FUNCTION(go_upper)
+{
+ zend_string *str;
+
+ ZEND_PARSE_PARAMETERS_START(1, 1)
+ Z_PARAM_STR(str)
+ ZEND_PARSE_PARAMETERS_END();
+
+ zend_string *result = go_upper(str);
+ RETVAL_STR(result);
+}
+```
+
+Puoi saperne di più su `ZEND_PARSE_PARAMETERS_START` e sull'analisi dei parametri nella pagina dedicata del libro [PHP Internals](https://www.phpinternalsbook.com/php7/extensions_design/php_functions.html#parsing-parameters-zend-parse-parameters). Qui diciamo a PHP che la nostra funzione accetta un parametro obbligatorio di tipo `string` come `zend_string`. Passiamo quindi questa stringa direttamente alla nostra funzione Go e restituiamo il risultato utilizzando `RETVAL_STR`.
+
+Resta solo una cosa da fare: implementare la funzione `go_upper` in Go.
+
+#### Implementa la funzione Vai
+
+La nostra funzione Go prenderà un `*C.zend_string` come parametro, lo convertirà in una stringa Go utilizzando la funzione helper di FrankenPHP, lo elaborerà e restituirà il risultato come un nuovo `*C.zend_string`. Le funzioni di supporto gestiscono per noi tutta la complessità della gestione della memoria e della conversione.
+
+```go
+// extension.go
+package example
+
+// #include
+import "C"
+import (
+ "unsafe"
+ "strings"
+
+ "github.com/dunglas/frankenphp"
+)
+
+//export go_upper
+func go_upper(s *C.zend_string) *C.zend_string {
+ str := frankenphp.GoString(unsafe.Pointer(s))
+
+ upper := strings.ToUpper(str)
+
+ return (*C.zend_string)(frankenphp.PHPString(upper, false))
+}
+```
+
+Questo approccio è molto più pulito e sicuro della gestione manuale della memoria.
+Le funzioni di supporto di FrankenPHP gestiscono automaticamente la conversione tra il formato `zend_string` di PHP e le stringhe Go.
+Il parametro `false` in `PHPString()` indica che vogliamo creare una nuova stringa non persistente (liberata alla fine della richiesta).
+
+> [!TIP]
+>
+> In questo esempio, non gestiamo gli errori, ma si dovrebbe sempre verificare che i puntatori non siano `nil` e che i dati siano validi prima di utilizzarli nelle funzioni Go.
+
+### Integrazione dell'estensione in FrankenPHP
+
+La nostra estensione è ora pronta per essere compilata e integrata in FrankenPHP. Per fare ciò, fare riferimento alla [documentazione di compilazione] di FrankenPHP(compile.md) per sapere come compilare FrankenPHP. Aggiungi il modulo utilizzando il flag `--with`, che punta al percorso del modulo:
+
+```console
+CGO_ENABLED=1 \
+XCADDY_GO_BUILD_FLAGS="-ldflags='-w -s' -tags=nobadger,nomysql,nopgx" \
+CGO_CFLAGS=$(php-config --includes) \
+CGO_LDFLAGS="$(php-config --ldflags) $(php-config --libs)" \
+xcaddy build \
+ --output frankenphp \
+ --with github.com/my-account/my-module
+```
+
+Questo è tutto! L'estensione è ora integrata in FrankenPHP e può essere utilizzata nel codice PHP.
+
+### Testare l'estensione
+
+Dopo aver integrato l'estensione in FrankenPHP, si può creare un file `index.php` con esempi per le funzioni che appena implementate:
+
+```php
+ [!WARNING]
+>
+> Questa funzionalità è destinata esclusivamente agli **ambienti di sviluppo**.
+> Non abilitare `hot_reload` in produzione, poiché questa funzionalità non è sicura (espone dettagli interni sensibili) e rallenta l'applicazione.
+
+```caddyfile
+localhost
+
+mercure {
+ anonymous
+}
+
+root public/
+php_server {
+ hot_reload
+}
+```
+
+Per impostazione predefinita, FrankenPHP controllerà tutti i file nella cartella di lavoro corrente che corrispondono a questo modello glob: `./**/*.{css,env,gif,htm,html,jpg,jpeg,js,mjs,php,png,svg,twig,webp,xml,yaml,yml}`
+
+È possibile impostare i file da monitorare utilizzando esplicitamente la sintassi glob:
+
+```caddyfile
+localhost
+
+mercure {
+ anonymous
+}
+
+root public/
+php_server {
+ hot_reload src/**/*{.php,.js} config/**/*.yaml
+}
+```
+
+Utilizza la forma lunga `hot_reload` per specificare l'argomento Mercure da utilizzare, nonché quali cartelle o file controllare:
+
+```caddyfile
+localhost
+
+mercure {
+ anonymous
+}
+
+root public/
+php_server {
+ hot_reload {
+ topic hot-reload-topic
+ watch src/**/*.php
+ watch assets/**/*.{ts,json}
+ watch templates/
+ watch public/css/
+ }
+}
+```
+
+## Integrazione lato client per la ricarica a caldo di FrankenPHP
+
+Mentre il server rileva le modifiche, il browser deve iscriversi a questi eventi per aggiornare la pagina.
+FrankenPHP espone l'URL Mercure Hub da utilizzare per sottoscrivere le modifiche ai file tramite la variabile di ambiente `$_SERVER['FRANKENPHP_HOT_RELOAD']`.
+
+È inoltre disponibile una comoda libreria JavaScript, [frankenphp-hot-reload](https://www.npmjs.com/package/frankenphp-hot-reload), per gestire la logica lato client.
+Per usarlo, aggiungi quanto segue al layout principale:
+
+```php
+
+FrankenPHP Hot Reload
+
+
+
+
+
+```
+
+La libreria si iscriverà automaticamente all'hub Mercure, recupererà l'URL corrente in background quando viene rilevata una modifica al file e trasformerà il DOM.
+È disponibile come pacchetto [npm](https://www.npmjs.com/package/frankenphp-hot-reload) e su [GitHub](https://github.com/dunglas/frankenphp-hot-reload).
+
+In alternativa, si può implementare una logica lato client iscrivendosi direttamente all'hub Mercure, usando la classe JavaScript nativa `EventSource`.
+
+### Preservazione dei nodi DOM esistenti
+
+In rari casi, come quando si utilizzano strumenti di sviluppo [come la barra degli strumenti di debug web di Symfony](https://github.com/symfony/symfony/pull/62970),
+potresti voler preservare specifici nodi DOM.
+Per fare ciò, aggiungi l'attributo `data-frankenphp-hot-reload-preserve` all'elemento HTML pertinente:
+
+```html
+
+```
+
+## Ricarica a caldo con la modalità worker FrankenPHP
+
+Se stai eseguendo l'applicazione in [Modalità di lavoro](https://frankenphp.dev/docs/worker/), lo script dell'applicazione rimane in memoria.
+Ciò significa che le modifiche al codice PHP non verranno applicate immediatamente, anche se il browser si ricarica.
+
+Per la migliore esperienza degli sviluppatori, dovresti combinare `hot_reload` con [la sottodirettiva `watch` nella direttiva `worker`](config.md#watching-for-file-changes).
+
+- `hot_reload`: aggiorna il **browser** quando i file cambiano
+- `worker.watch`: riavvia il worker quando i file cambiano
+
+```caddyfile
+# Caddyfile: combine FrankenPHP hot reload with worker watch for full dev workflow
+localhost
+
+mercure {
+ anonymous
+}
+
+root public/
+php_server {
+ hot_reload
+ worker {
+ file /path/to/my_worker.php
+ watch
+ }
+}
+```
+
+## Come funziona la ricarica a caldo di FrankenPHP
+
+1. **Guarda**: FrankenPHP monitora il filesystem per eventuali modifiche utilizzando [la libreria `e-dant/watcher`](https://github.com/e-dant/watcher) dietro le quinte (abbiamo contribuito con il collegamento Go).');
+2. **Riavvia (modalità worker)**: se `watch` è abilitato nella configurazione del worker, il worker PHP viene riavviato per caricare il nuovo codice.
+3. **Push**: un payload JSON contenente l'elenco dei file modificati viene inviato al [Mercure hub](https://mercure.rocks) integrato.
+4. **Ricevi**: Il browser, in ascolto tramite la libreria JavaScript, riceve l'evento Mercure.
+5. **Aggiornamento**:
+
+- Se viene rilevato **Idiomorph**, recupera il contenuto aggiornato e trasforma l'HTML corrente in modo che corrisponda al nuovo stato, applicando le modifiche istantaneamente senza perdere lo stato.
+- Altrimenti, viene chiamato `window.location.reload()` per aggiornare la pagina.
diff --git a/docs/it/known-issues.md b/docs/it/known-issues.md
new file mode 100644
index 0000000000..90ea2a1bb8
--- /dev/null
+++ b/docs/it/known-issues.md
@@ -0,0 +1,148 @@
+# Problemi noti
+
+## Estensioni PHP non supportate
+
+Le seguenti estensioni non sono compatibili con FrankenPHP:
+
+| Nome | Motivo | Alternative |
+| ----------------------------------------------------------------------------------------------------------- | --------------- | ------------------------------------------------------------------------------------------------------------------- |
+| [imap](https://www.php.net/manual/en/imap.installation.php) | Non thread-safe | [javanile/php-imap2](https://github.com/javanile/php-imap2), [webklex/php-imap](https://github.com/Webklex/php-imap) |
+| [nuova reliquia](https://docs.newrelic.com/docs/apm/agents/php-agent/getting-started/introduction-new-relic-php/) | Non thread-safe | - |
+
+## Estensioni PHP difettose
+
+Le seguenti estensioni presentano bug noti e comportamenti imprevisti se utilizzate con FrankenPHP:
+
+| Nome | Problema |
+| ------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
+| [ext-openssl](https://www.php.net/manual/en/book.openssl.php) | Quando si utilizza musl libc, l'estensione OpenSSL potrebbe bloccarsi in caso di carichi pesanti. Il problema non si verifica quando si utilizza la più popolare libc GNU. Questo bug è [monitorato da PHP](https://github.com/php/php-src/issues/13648). |
+
+## get_browser
+
+La funzione [get_browser()](https://www.php.net/manual/en/function.get-browser.php) sembra funzionare male dopo un po'. Una soluzione alternativa consiste nel memorizzare nella cache (ad esempio con [APCu](https://www.php.net/manual/en/book.apcu.php)) i risultati per agente utente, poiché sono statici.
+
+## Immagini Docker binarie autonome e basate su Alpine
+
+Le immagini Docker binarie completamente statiche e basate su Alpine (`dunglas/frankenphp:*-alpine`) utilizzano [musl libc](https://musl.libc.org/) invece di [glibc e amici](https://www.etalabs.net/compare_libcs.html), per mantenere una dimensione binaria più piccola.
+Ciò potrebbe portare ad alcuni problemi di compatibilità.
+In particolare, il flag glob `GLOB_BRACE` [non è disponibile](https://www.php.net/manual/en/function.glob.php)
+
+Se si riscontrano problemi, utilizzare la variante GNU del binario statico e delle immagini Docker basate su Debian.
+
+## Utilizzo di `https://127.0.0.1` con Docker
+
+Per impostazione predefinita, FrankenPHP genera un certificato TLS per `localhost`.
+È l'opzione più semplice e consigliata per lo sviluppo locale.
+
+Se invece si vuole utilizzare `127.0.0.1` come host, è possibile configurarlo per generare un certificato impostando il nome del server su `127.0.0.1`.
+
+Sfortunatamente, questo non è sufficiente quando si utilizza Docker, a causa del [suo sistema di rete](https://docs.docker.com/network/).
+Si riceverà un errore TLS simile a `curl: (35) LibreSSL/3.3.6: error:1404B438:SSL routines:ST_CONNECT:tlsv1 alert internal error`.
+
+Se si usa Linux, una soluzione è utilizzare [il driver di rete host](https://docs.docker.com/network/network-tutorial-host/):
+
+```console
+docker run \
+ -e SERVER_NAME="127.0.0.1" \
+ -v $PWD:/app/public \
+ --network host \
+ dunglas/frankenphp
+```
+
+Il driver di rete host non è supportato su Mac e Windows. Su queste piattaforme si dovrà ricavare l'indirizzo IP del contenitore e includerlo nei nomi dei server.
+
+Eseguire `docker network inspect bridge` e trovare la chiave `Containers` per identificare l'ultimo indirizzo IP attualmente assegnato sotto la chiave `IPv4Address` e incrementarlo di uno. Se non è in esecuzione alcun contenitore, il primo indirizzo IP assegnato è solitamente `172.17.0.2`.
+
+Quindi, includerlo nella variabile di ambiente `SERVER_NAME`:
+
+```console
+docker run \
+ -e SERVER_NAME="127.0.0.1, 172.17.0.3" \
+ -v $PWD:/app/public \
+ -p 80:80 -p 443:443 -p 443:443/udp \
+ dunglas/frankenphp
+```
+
+> [!CAUTION]
+>
+> Assicurarsi di sostituire `172.17.0.3` con l'IP che verrà assegnato al contenitore.
+
+Ora dovrebbe essere possibile accedere a `https://127.0.0.1` dal computer host.
+
+In caso contrario, avviare FrankenPHP in modalità debug per cercare di capire il problema:
+
+```console
+docker run \
+ -e CADDY_GLOBAL_OPTIONS="debug" \
+ -e SERVER_NAME="127.0.0.1" \
+ -v $PWD:/app/public \
+ -p 80:80 -p 443:443 -p 443:443/udp \
+ dunglas/frankenphp
+```
+
+## Script di composer che fanno riferimento a `@php`
+
+[Gli script di composer](https://getcomposer.org/doc/articles/scripts.md) potrebbero voler eseguire un binario PHP per alcune attività, ad es. in [un progetto Laravel](laravel.md) per eseguire `@php artisan package:discover --ansi`. Questo [attualmente fallisce](https://github.com/php/frankenphp/issues/483#issuecomment-1899890915) per due motivi:
+
+- composer non sa come chiamare il binario FrankenPHP;
+- composer può aggiungere impostazioni PHP utilizzando il flag `-d` nel comando, che FrankenPHP non supporta ancora.
+
+Come soluzione alternativa, possiamo creare uno script di shell in `/usr/local/bin/php` che rimuove i parametri non supportati e quindi chiama FrankenPHP:
+
+```bash
+#!/usr/bin/env bash
+# /usr/local/bin/php
+args=("$@")
+index=0
+for i in "$@"
+do
+ if [ "$i" == "-d" ]; then
+ unset 'args[$index]'
+ unset 'args[$index+1]'
+ fi
+ index=$((index+1))
+done
+
+/usr/local/bin/frankenphp php-cli ${args[@]}
+```
+
+Quindi impostare la variabile di ambiente `PHP_BINARY` sul percorso dello script `php` ed eseguire composer:
+
+```console
+export PHP_BINARY=/usr/local/bin/php
+composer install
+```
+
+## Risoluzione dei problemi TLS/SSL con file binari statici
+
+Quando si utilizzano i file binari statici, è possibile che si verifichino i seguenti errori relativi a TLS, ad esempio quando si inviano e-mail utilizzando STARTTLS:
+
+```text
+Unable to connect with STARTTLS: stream_socket_enable_crypto(): SSL operation failed with code 5. OpenSSL Error messages:
+error:80000002:system library::No such file or directory
+error:80000002:system library::No such file or directory
+error:80000002:system library::No such file or directory
+error:0A000086:SSL routines::certificate verify failed
+```
+
+Poiché il file binario statico non include i certificati TLS, è necessario indirizzare OpenSSL all'installazione dei certificati della CA locale.
+
+Esaminare l'output di [`openssl_get_cert_locations()`](https://www.php.net/manual/en/function.openssl-get-cert-locations.php),
+per trovare dove devono essere installati i certificati CA e archiviarli in questa posizione.
+
+> [!WARNING]
+>
+> I contesti Web e CLI possono avere impostazioni diverse.
+> Assicurarsi di eseguire `openssl_get_cert_locations()` nel contesto corretto.
+
+[I certificati CA estratti da Mozilla possono essere scaricati sul sito cURL](https://curl.se/docs/caextract.html).
+
+In alternativa, molte distribuzioni, tra cui Debian, Ubuntu e Alpine, forniscono pacchetti denominati `ca-certificates` che contengono questi certificati.
+
+È anche possibile utilizzare `SSL_CERT_FILE` e `SSL_CERT_DIR` per suggerire a OpenSSL dove cercare i certificati CA:
+
+```console
+# Imposta le variabili d'ambiente dei certificati TLS
+export SSL_CERT_FILE=/etc/ssl/certs/ca-certificates.crt
+export SSL_CERT_DIR=/etc/ssl/certs
+```
diff --git a/docs/it/laravel.md b/docs/it/laravel.md
new file mode 100644
index 0000000000..5e4bae8078
--- /dev/null
+++ b/docs/it/laravel.md
@@ -0,0 +1,217 @@
+# Laravel
+
+## Esecuzione di Laravel con l'immagine Docker di FrankenPHP
+
+Servire un'applicazione web [Laravel](https://laravel.com) con FrankenPHP è facile come montare il progetto nella cartella `/app` dell'immagine Docker ufficiale.
+
+Eseguire questo comando dalla cartella principale dell'app Laravel:
+
+```console
+docker run -p 80:80 -p 443:443 -p 443:443/udp -v $PWD:/app dunglas/frankenphp
+```
+
+Buon diverimento!
+
+## Installazione di Laravel con FrankenPHP in locale
+
+In alternativa, si possono eseguire progetti Laravel con FrankenPHP dal computer locale:
+
+1. [Scaricare il binario corrispondente al sistema](../#standalone-binary)
+2. Aggiungere la seguente configurazione a un file denominato `Caddyfile` nella cartella root del progetto Laravel:
+
+ ```caddyfile
+ # Caddyfile
+ {
+ frankenphp
+ }
+
+ # Nome dominio del server
+ localhost {
+ # Imposta la webroot alla cartella public/
+ root public/
+ # Abilita la compressione (facoltativo)
+ encode zstd br gzip
+ # Esegue i file PHP e serve i file da public/
+ php_server {
+ try_files {path} index.php
+ }
+ }
+ ```
+
+3. Avviare FrankenPHP dalla cartella principale del progetto Laravel: `frankenphp run`
+
+## Laravel Octane
+
+Octane può essere installato tramite il gestore pacchetti Composer:
+
+```console
+composer require laravel/octane
+```
+
+Dopo aver installato Octane, si può eseguire il comando artisan `octane:install`, che installerà il file di configurazione di Octane nell'applicazione:
+
+```console
+php artisan octane:install --server=frankenphp
+```
+
+Il server Octane può essere avviato tramite il comando artisan `octane:frankenphp`.
+
+```console
+php artisan octane:frankenphp
+```
+
+Il comando `octane:frankenphp` accetta le seguenti opzioni:
+
+- `--host`: l'indirizzo IP a cui il server deve associarsi (impostazione predefinita: `127.0.0.1`)
+- `--port`: la porta su cui deve essere disponibile il server (impostazione predefinita: `8000`)
+- `--admin-port`: la porta su cui deve essere disponibile il server di amministrazione (impostazione predefinita: `2019`)
+- `--workers`: il numero di worker che dovrebbero essere disponibili per gestire le richieste (impostazione predefinita: `auto`)
+- `--max-requests`: il numero di richieste da elaborare prima di ricaricare il server (impostazione predefinita: `500`)
+- `--caddyfile`: il percorso del file FrankenPHP `Caddyfile` (impostazione predefinita: [stubbed `Caddyfile` in Laravel Octane](https://github.com/laravel/octane/blob/2.x/src/Commands/stubs/Caddyfile))
+- `--https`: abilita HTTPS, HTTP/2 e HTTP/3 e genera e rinnova automaticamente i certificati
+- `--http-redirect`: abilita il reindirizzamento da HTTP a HTTPS (abilitato solo se viene passato --https)
+- `--watch`: ricarica automaticamente il server quando l'applicazione viene modificata
+- `--poll`: utilizza il polling del file system durante la visione per osservare i file su una rete
+- `--log-level`: registra i messaggi al livello di log specificato o superiore, utilizzando il logger Caddy nativo
+
+> [!TIP]
+> Per ottenere log JSON strutturati (utili quando si utilizzano soluzioni di analisi dei log), passare esplicitamente l'opzione `--log-level`.
+
+Vedi anche [come utilizzare Mercure con Octane](#mercure-support).
+
+Saperne di più su [Laravel Octane nella documentazione ufficiale](https://laravel.com/docs/octane).
+
+## App Laravel come file binari autonomi
+
+Utilizzando la [funzione di incorporamento dell'applicazione di FrankenPHP](embed.md), è possibile distribuire Laravel
+app come file binari autonomi.
+
+Seguire questi passaggi per creare il pacchetto dell'app Laravel come binario autonomo per Linux:
+
+1. Creare un file chiamato `static-build.Dockerfile` nel repository dell'app:
+
+ ```dockerfile
+ # static-build.Dockerfile
+ FROM --platform=linux/amd64 dunglas/frankenphp:static-builder-gnu
+ # Se si vuole eseguire il binario su sistemi musl-libc, usare invece static-builder-musl
+
+ # Copia l'app
+ WORKDIR /go/src/app/dist/app
+ COPY . .
+
+ # Rimuove i test e altri file supeflui, per risparmiare spazio
+ # Si possono anche aggiungere tali file a .dockerignore
+ RUN rm -Rf tests/
+
+ # Copia il file .env
+ RUN cp .env.example .env
+ # Cambia APP_ENV e APP_DEBUG per la produzione
+ RUN sed -i'' -e 's/^APP_ENV=.*/APP_ENV=production/' -e 's/^APP_DEBUG=.*/APP_DEBUG=false/' .env
+
+ # Altre modifiche al file .env, se necessario
+
+ # Installa le dipendenze
+ RUN composer install --ignore-platform-reqs --no-dev -a
+
+ # Costruisce il binario statico
+ WORKDIR /go/src/app/
+ RUN EMBED=dist/app/ ./build-static.sh
+ ```
+
+ > [!CAUTION]
+ >
+ > Alcuni file `.dockerignore`
+ > ignorano la cartella `vendor/` e i file `.env`. Assicurarsi di modificare o rimuovere il file `.dockerignore` prima della compilazione.
+
+2. Build:
+
+ ```console
+ docker build -t static-laravel-app -f static-build.Dockerfile .
+ ```
+
+3. Estrarre il file binario:
+
+ ```console
+ docker cp $(docker create --name static-laravel-app-tmp static-laravel-app):/go/src/app/dist/frankenphp-linux-x86_64 frankenphp ; docker rm static-laravel-app-tmp
+ ```
+
+4. Popolare le cache:
+
+ ```console
+ frankenphp php-cli artisan optimize
+ ```
+
+5. Eseguire le migrazioni del database (se presenti):
+
+ ```console
+ frankenphp php-cli artisan migrate
+ ```
+
+6. Generare la chiave segreta dell'app:
+
+ ```console
+ frankenphp php-cli artisan key:generate
+ ```
+
+7. Avviare il server:
+
+ ```console
+ frankenphp php-server
+ ```
+
+La nuova app è ora pronta!
+
+Ulteriori informazioni sulle opzioni disponibili e su come creare file binari per altri sistemi operativi si possono trovare nella documentazione sull'[embed di applicazioni](embed.md).
+
+### Modifica del percorso di archiviazione
+
+Per impostazione predefinita, Laravel archivia file, cache, log, ecc. caricati nella cartella `storage/` dell'applicazione.
+Questo non è adatto per le applicazioni integrate, poiché ogni nuova versione verrà estratta in una cartella temporanea diversa.
+
+Imposta la variabile di ambiente `LARAVEL_STORAGE_PATH` (ad esempio, nel file `.env`) o chiama il metodo `Illuminate\Foundation\Application::useStoragePath()` per utilizzare una cartella esterna a quella temporanea.
+
+### Supporto Mercure
+
+[Mercure](https://mercure.rocks) è un ottimo modo per aggiungere funzionalità di real time alle app Laravel.
+FrankenPHP include [supporto Mercure pronto all'uso](mercure.md).
+
+Se non utilizzi [Octane](#laravel-octane), consulta [la voce della documentazione Mercure](mercure.md).
+
+Se si usa Octane, si può abilitare il supporto Mercure aggiungendo le seguenti righe al file `config/octane.php`:
+
+```php
+// config/octane.php
+// ...
+
+return [
+ // ...
+
+ 'mercure' => [
+ 'anonymous' => true,
+ 'publisher_jwt' => '!ChangeThisMercureHubJWTSecretKey!',
+ 'subscriber_jwt' => '!ChangeThisMercureHubJWTSecretKey!',
+ ],
+];
+```
+
+È possibile utilizzare [tutte le direttive supportate da Mercure](https://mercure.rocks/docs/hub/config#directives) in questo array.
+
+Per pubblicare e sottoscrivere gli aggiornamenti, ti consigliamo di utilizzare la libreria [Laravel Mercure Broadcaster](https://github.com/mvanduijker/laravel-mercure-broadcaster).
+In alternativa, consulta [la documentazione Mercure](mercure.md) per farlo in puro PHP e JavaScript.
+
+### Esecuzione di Octane con file binari autonomi
+
+È anche possibile impacchettare le app Laravel Octane come file binari autonomi!
+
+Per fare ciò, [installa Octane correttamente](#laravel-octane) e segui i passaggi descritti nella [sezione sulle app Laravel come binari autonomi](#laravel-apps-as-standalone-binaries).
+
+Quindi, per avviare FrankenPHP in modalità worker tramite Octane, eseguire:
+
+```console
+PATH="$PWD:$PATH" frankenphp php-cli artisan octane:frankenphp
+```
+
+> [!CAUTION]
+>
+> Affinché il comando funzioni, il file binario autonomo **deve** chiamarsi `frankenphp`,
+> perché Octane necessita di un programma chiamato `frankenphp` disponibile nel percorso.
diff --git a/docs/it/mercure.md b/docs/it/mercure.md
new file mode 100644
index 0000000000..07ca3f2329
--- /dev/null
+++ b/docs/it/mercure.md
@@ -0,0 +1,151 @@
+# Real time
+
+FrankenPHP viene fornito con un hub [Mercure](https://mercure.rocks) integrato!
+Mercure ti consente di inviare eventi in tempo reale a tutti i dispositivi connessi: riceveranno immediatamente un evento JavaScript.
+
+È una comoda alternativa ai WebSocket, semplice da usare e supportata nativamente da tutti i browser Web moderni!
+
+
+
+## Abilitare Mercure
+
+Il supporto Mercure è disabilitato per impostazione predefinita.
+Ecco un esempio minimo di `Caddyfile` che abilita sia FrankenPHP sia l'hub Mercure:
+
+```caddyfile
+# Hostname a cui rispondere
+localhost
+
+mercure {
+ # Il secret usato per firmare i token JWT per i publisher
+ publisher_jwt !ChangeThisMercureHubJWTSecretKey!
+ # Se si imposta publisher_jwt, si deve impostare anche subscriber_jwt
+ subscriber_jwt !ChangeThisMercureHubJWTSecretKey!
+ # Consnete subscriber anonimi (senzsa JWT)
+ anonymous
+}
+
+root public/
+php_server
+```
+
+> [!TIP]
+>
+> L'[esempio di `Caddyfile`](https://github.com/php/frankenphp/blob/main/caddy/frankenphp/Caddyfile)
+> fornito dalle [immagini Docker](docker.md) include già una configurazione Mercure commentata
+> con comode variabili d'ambiente per configurarlo.
+>
+> Decommentare la sezione Mercure in `/etc/frankenphp/Caddyfile` per abilitarla.
+
+## Iscrizione agli aggiornamenti
+
+Per impostazione predefinita, l'hub Mercure è disponibile nel percorso `/.well-known/mercure` del server FrankenPHP.
+Per iscriversi agli aggiornamenti, utilizzare la classe JavaScript nativa [`EventSource`](https://developer.mozilla.org/docs/Web/API/EventSource):
+
+```html
+
+
+Mercure Example
+
+```
+
+## Pubblicazione aggiornamenti
+
+### Utilizzo di `mercure_publish()`
+
+FrankenPHP fornisce una comoda funzione `mercure_publish()` per pubblicare aggiornamenti sull'hub Mercure integrato:
+
+```php
+ 'value']));
+
+// Scrive nel log di FrankenPHP
+error_log("update $updateID published", 4);
+```
+
+La firma completa della funzione è:
+
+```php
+/**
+ * @param string|string[] $topics
+ */
+function mercure_publish(string|array $topics, string $data = '', bool $private = false, ?string $id = null, ?string $type = null, ?int $retry = null): string {}
+```
+
+### Utilizzo di `file_get_contents()`
+
+Per inviare un aggiornamento ai subscriber connessi, inviare una richiesta POST autenticata all'hub Mercure con i parametri `topic` e `data`:
+
+```php
+ [
+ 'method' => 'POST',
+ 'header' => "Content-type: application/x-www-form-urlencoded\r\nAuthorization: Bearer " . JWT,
+ 'content' => http_build_query([
+ 'topic' => 'my-topic',
+ 'data' => json_encode(['key' => 'value']),
+ ]),
+]]));
+
+// Scrive nel log di FrankenPHP
+error_log("update $updateID published", 4);
+```
+
+La chiave passata come parametro dell'opzione `mercure.publisher_jwt` in `Caddyfile` deve essere utilizzata per firmare il token JWT utilizzato nell'header `Authorization`.
+
+Il JWT deve includere un'attestazione `mercure` con un'autorizzazione `publish` per gli argomenti da pubblicare.
+Consultare la [documentazione Mercure](https://mercure.rocks/spec#publishers) sull'autorizzazione.
+
+Per generare i propri token, si può utilizzare [questo link jwt.io](https://www.jwt.io/#token=eyJhbGciOiJIUzI1NiJ9.eyJtZXJjdXJlIjp7InB1Ymxpc2giOlsiKiJdfX0.PXwpfIGng6KObfZlcOXvcnWCJOWTFLtswGI5DZuWSK4),
+ma per le app di produzione, è consigliabile utilizzare token di breve durata generati dinamicamente utilizzando una [libreria JWT](https://www.jwt.io/libraries?programming_language=php) attendibile.
+
+### Utilizzo di Symfony Mercure
+
+In alternativa, si può utilizzare il [Componente Symfony Mercure](https://symfony.com/components/Mercure), una libreria PHP autonoma.
+
+Questa libreria gestisce la generazione JWT, la pubblicazione degli aggiornamenti e l'autorizzazione basata su cookie per i subscriber.
+
+Innanzitutto, installare la libreria utilizzando Composer:
+
+```console
+composer require symfony/mercure lcobucci/jwt
+```
+
+Si può quindi usare in questo modo:
+
+```php
+publish(new \Symfony\Component\Mercure\Update('my-topic', json_encode(['key' => 'value'])));
+
+// Scrive nel log di FrankenPHP
+error_log("update $updateID published", 4);
+```
+
+Mercure è nativamente supportato anche da:
+
+- [Laravel](laravel.md#mercure-support)
+- [Symfony](https://symfony.com/doc/current/mercure.html)
+- [API Platform](https://api-platform.com/docs/core/mercure/)
diff --git a/docs/it/metrics.md b/docs/it/metrics.md
new file mode 100644
index 0000000000..33fb48723e
--- /dev/null
+++ b/docs/it/metrics.md
@@ -0,0 +1,20 @@
+# Metriche
+
+> [!TIP]
+> Per una configurazione completa dell'osservabilità, compresi dashboard in tempo reale e monitoraggio della produzione, consultare la pagina [Osservabilità](observability.md).
+
+Quando le [metriche Caddy](https://caddyserver.com/docs/metrics) sono abilitate, FrankenPHP espone le seguenti metriche:
+
+- `frankenphp_total_threads`: il numero totale di thread PHP.
+- `frankenphp_busy_threads`: il numero di thread PHP che attualmente elaborano una richiesta (i worker in esecuzione consumano sempre un thread).
+- `frankenphp_queue_depth`: il numero di richieste regolari in coda
+- `frankenphp_total_workers{worker="[worker_name]"}`: numero totale di worker.
+- `frankenphp_busy_workers{worker="[worker_name]"}`: il numero di worker che attualmente elaborano una richiesta.
+- `frankenphp_worker_request_time{worker="[worker_name]"}`: tempo impiegato per elaborare le richieste di tutti i worker.
+- `frankenphp_worker_request_count{worker="[worker_name]"}`: numero di richieste elaborate da tutti i worker.
+- `frankenphp_ready_workers{worker="[worker_name]"}`: il numero di worker che hanno chiamato `frankenphp_handle_request` almeno una volta.
+- `frankenphp_worker_crashes{worker="[worker_name]"}`: il numero di volte in cui un worker è stato licenziato in modo imprevisto.
+- `frankenphp_worker_restarts{worker="[worker_name]"}`: numero di volte in cui un worker è stato riavviato deliberatamente.
+- `frankenphp_worker_queue_depth{worker="[worker_name]"}`: il numero di richieste in coda.
+
+Per le metriche dei worker, il segnaposto `[worker_name]` viene sostituito dal nome del worker nel Caddyfile, altrimenti verrà utilizzato il percorso assoluto del file del worker.
diff --git a/docs/it/performance.md b/docs/it/performance.md
new file mode 100644
index 0000000000..84e3e8aa53
--- /dev/null
+++ b/docs/it/performance.md
@@ -0,0 +1,200 @@
+# Prestazioni
+
+Per impostazione predefinita, FrankenPHP cerca di offrire un buon compromesso tra prestazioni e facilità d'uso.
+Tuttavia, è possibile migliorare sostanzialmente le prestazioni utilizzando una configurazione appropriata.
+
+## Ottimizzazione dei thread e dei worker
+
+Per impostazione predefinita, FrankenPHP avvia un numero di thread e worker due volte superiore (in modalità worker) rispetto al numero disponibile di core della CPU.
+
+I valori appropriati dipendono fortemente da come è scritta l'applicazione, da cosa fa e dall'hardware.
+Consigliamo vivamente di modificare questi valori. Per la migliore stabilità del sistema, si consiglia di avere `num_threads` x `memory_limit` < `available_memory`.
+
+Per trovare i valori corretti, è meglio eseguire test di carico simulando il traffico reale.
+[k6](https://k6.io) e [Gatling](https://gatling.io) sono ottimi strumenti per questo.
+
+Per configurare il numero di thread, utilizzare l'opzione `num_threads` delle direttive `php_server` e `php`.
+Per modificare il numero di worker, utilizzare l'opzione `num` della sezione `worker` della direttiva `frankenphp`.
+
+### `max_threads`
+
+Sebbene sia sempre meglio sapere esattamente come sarà il traffico, le applicazioni nella vita reale tendono ad essere più
+imprevedibili. La [configurazione](config.md#caddyfile-config) `max_threads` consente a FrankenPHP di generare automaticamente thread aggiuntivi in fase di esecuzione fino al limite specificato.
+`max_threads` può aiutare a capire quanti thread sono necessari per gestire il traffico e può rendere il server più resistente ai picchi di latenza.
+Se impostato su `auto`, il limite verrà stimato in base a `memory_limit` in `php.ini`. Se non è in grado di farlo,
+`auto` verrà invece impostato per impostazione predefinita sul doppio di `num_threads`. Si tenga presente che `auto` potrebbe sottostimare fortemente il numero di thread necessari.
+`max_threads` è simile a [pm.max_children](https://www.php.net/manual/en/install.fpm.configuration.php#pm.max-children) di PHP FPM. La differenza principale è che FrankenPHP utilizza i thread invece di
+processi e li delega automaticamente tra diversi worker e "modalità classica" in base alle esigenze.
+
+## Modalità worker per una maggiore produttività
+
+L'abilitazione della [modalità di lavoro FrankenPHP](worker.md) migliora notevolmente le prestazioni,
+ma l'app deve essere adattata per essere compatibile con questa modalità:
+è necessario creare un worker ed essere sicuri che l'app non perda memoria.
+
+## Evitare musl in produzione: meglio le build glibc
+
+La variante Alpine Linux delle immagini Docker ufficiali e i file binari predefiniti che forniamo utilizzano [musl libc](https://musl.libc.org).
+
+PHP è noto per essere [più lento](https://gitlab.alpinelinux.org/alpine/aports/-/issues/14381) quando si utilizza questa libreria C alternativa invece della tradizionale libreria GNU,
+soprattutto se compilato in modalità ZTS (thread-safe), richiesta per FrankenPHP. La differenza può essere significativa in un ambiente con numerosi thread.
+
+Inoltre, [alcuni bug si verificano solo quando si utilizza musl](https://github.com/php/php-src/issues?q=sort%3Aupdated-desc+is%3Aissue+is%3Aopen+label%3ABug+musl).
+
+Negli ambienti di produzione, consigliamo di utilizzare FrankenPHP collegato a glibc, compilato con un livello di ottimizzazione appropriato.
+
+Ciò può essere ottenuto utilizzando le immagini Debian Docker, utilizzando [i pacchetti .deb, .rpm o .apk dei nostri manutentori](https://pkgs.henderkes.com) o [compilando FrankenPHP dai sorgenti](compile.md).
+
+Per contenitori più snelli o più sicuri, potresti prendere in considerazione [un'immagine Debian rafforzata](docker.md#hardening-images) anziché Alpine.
+
+## Configurazione runtime di Go per FrankenPHP
+
+FrankenPHP è scritto in Go.
+
+In generale, il runtime Go non richiede alcuna configurazione speciale, ma in determinate circostanze,
+la configurazione specifica migliora le prestazioni.
+
+Probabilmente si vorrà impostare la variabile di ambiente `GODEBUG` su `cgocheck=0` (l'impostazione predefinita nelle immagini Docker FrankenPHP).
+
+Se si esegue FrankenPHP in contenitori (Docker, Kubernetes, LXC...) e la memoria disponibile per i contenitori è limitata,
+impostare la variabile di ambiente `GOMEMLIMIT` sulla quantità di memoria disponibile.
+
+Per ulteriori dettagli, fare riferimento alle [variabili di ambiente runtime Go](https://pkg.go.dev/runtime#hdr-Environment_Variables) per ottenere il massimo dal runtime.
+
+## `file_server`
+
+Per impostazione predefinita, la direttiva `php_server` configura automaticamente un file server su
+servire file statici (risorse) archiviati nella cartella principale.
+
+Questa funzionalità è conveniente, ma ha un costo.
+Per disabilitarlo, utilizzare la seguente configurazione:
+
+```caddyfile
+php_server {
+ file_server off
+}
+```
+
+## `try_files`
+
+Oltre ai file statici e ai file PHP, `php_server` proverà anche a servire l'indice dell'applicazione
+e file di indice della cartella (`/path/` -> `/path/index.php`). Se non si ha bisogno degli indici di cartelle,
+si possono disabilitare definendo esplicitamente `try_files` in questo modo:
+
+```caddyfile
+php_server {
+ try_files {path} index.php
+ root /root/to/your/app # explicitly adding the root here allows for better caching
+}
+```
+
+Ciò può ridurre significativamente il numero di operazioni sui file non necessarie.
+Un worker equivalente della configurazione precedente sarebbe:
+
+```caddyfile
+route {
+ php_server { # use "php" instead of "php_server" if you don't need the file server at all
+ root /root/to/your/app
+ worker /path/to/worker.php {
+ match * # send all requests directly to the worker
+ }
+ }
+}
+```
+
+Un approccio alternativo con zero operazioni non necessarie sul file system sarebbe invece quello di utilizzare la direttiva `php` e dividere
+file da PHP per percorso. Questo approccio funziona bene se l'intera applicazione è servita da un unico file di ingresso.
+Una [configurazione](config.md#caddyfile-config) di esempio che serve file statici dietro una cartella `/assets` potrebbe assomigliare a questa:
+
+```caddyfile
+# Caddyfile: split static assets and PHP requests to skip filesystem lookups
+route {
+ @assets {
+ path /assets/*
+ }
+
+ # everything behind /assets is handled by the file server
+ file_server @assets {
+ root /root/to/your/app
+ }
+
+ # everything that is not in /assets is handled by your index or worker PHP file
+ rewrite index.php
+ php {
+ root /root/to/your/app # explicitly adding the root here allows for better caching
+ }
+}
+```
+
+## Evitaew i segnaposto Caddyfile nei percorsi attivi
+
+È possibile utilizzare [segnaposto](https://caddyserver.com/docs/conventions#placeholders) nelle direttive `root` e `env`.
+Tuttavia, ciò impedisce la memorizzazione nella cache di questi valori e comporta un costo significativo in termini di prestazioni.
+
+Se possibile, evitare i segnaposto in queste direttive.
+
+## `resolve_root_symlink`
+
+Per impostazione predefinita, se la document root è un collegamento simbolico, viene automaticamente risolto da FrankenPHP (questo è necessario affinché PHP funzioni correttamente).
+Se la document root non è un collegamento simbolico, si può disabilitare questa funzione.
+
+```caddyfile
+php_server {
+ resolve_root_symlink false
+}
+```
+
+Ciò migliorerà le prestazioni se la direttiva `root` contiene [segnaposto](https://caddyserver.com/docs/conventions#placeholders).
+Negli altri casi il guadagno sarà trascurabile.
+
+## Prestazioni dei log
+
+I log sono molto utili, ma, per definizione,
+richiedono operazioni di I/O e allocazioni di memoria, il che riduce notevolmente le prestazioni.
+Assicurarsii di [impostare il livello di log](https://caddyserver.com/docs/caddyfile/options#log) correttamente,
+per salvare solo ciò che è necessario.
+
+## Ottimizzazione delle prestazioni PHP per FrankenPHP
+
+FrankenPHP utilizza l'interprete PHP ufficiale.
+Tutte le consuete ottimizzazioni delle prestazioni relative a PHP si applicano a FrankenPHP.
+
+In particolare:
+
+- controllare che [OPcache](https://www.php.net/manual/en/book.opcache.php) sia installato, abilitato e configurato correttamente
+- attivare le [ottimizzazioni del caricatore automatico Composer](https://getcomposer.org/doc/articles/autoloader-optimization.md)
+- assicurarsi che la cache di `realpath` sia sufficientemente grande per le esigenze dell'applicazione
+- utilizzare il [preloading](https://www.php.net/manual/en/opcache.preloading.php)
+
+Per maggiori dettagli, leggere [la documentazione sull'ottimizzazione delle prestazioni di Symfony](https://symfony.com/doc/current/performance.html)
+(la maggior parte dei suggerimenti sono utili anche se non usi Symfony).
+
+## Suddivisione del pool di thread FrankenPHP per endpoint lenti
+
+È normale che le applicazioni interagiscano con servizi esterni lenti, come un file
+API che tende a essere inaffidabile in condizioni di carico elevato o che impiega costantemente più di 10 secondi per rispondere.
+In questi casi, può essere utile dividere il pool di thread per avere pool "lenti" dedicati.
+Ciò impedisce agli endpoint lenti di consumare tutte le risorse/thread del server e
+limita la concorrenza delle richieste destinate all'endpoint lento, in modo simile a a
+pool di connessione.
+
+```caddyfile
+# Caddyfile: dedicated FrankenPHP thread pool for slow endpoints
+example.com {
+ php_server {
+ root /app/public # the root of your application
+ worker index.php {
+ match /slow-endpoint/* # all requests with path /slow-endpoint/* are handled by this thread pool
+ num 1 # minimum 1 threads for requests matching /slow-endpoint/*
+ max_threads 20 # allow up to 20 threads for requests matching /slow-endpoint/*, if needed
+ }
+ worker index.php {
+ match * # all other requests are handled separately
+ num 1 # minimum 1 threads for other requests, even if the slow endpoints start hanging
+ max_threads 20 # allow up to 20 threads for other requests, if needed
+ }
+ }
+}
+```
+
+In genere è consigliabile gestire anche gli endpoint molto lenti in modo asincrono, utilizzando meccanismi pertinenti come le code di messaggi.
diff --git a/docs/it/production.md b/docs/it/production.md
new file mode 100644
index 0000000000..f7b85eb85c
--- /dev/null
+++ b/docs/it/production.md
@@ -0,0 +1,168 @@
+# Deploy in produzione
+
+In questo tutorial impareremo come eseguire il deploy di un'applicazione PHP su un singolo server con Docker Compose.
+
+Se si usa Symfony, meglio far riferimento alla documentazione "[Deploy in produzione](https://github.com/dunglas/symfony-docker/blob/main/docs/production.md)" del progetto Symfony Docker (che utilizza FrankenPHP).
+
+Se si usa API Platform (che utilizza anche FrankenPHP), fare riferimento alla [documentazione del framework](https://api-platform.com/docs/deployment/).
+
+## Preparazione dell'app
+
+Innanzitutto, creare un `Dockerfile` nella cartella principale del progetto:
+
+```dockerfile
+FROM dunglas/frankenphp
+
+# Assicurarsi di sostituire "your-domain-name.example.com" col nome di dominio desiderato
+ENV SERVER_NAME=your-domain-name.example.com
+# Se si vole disabilitare HTTPS, usare invece questo valore:
+#ENV SERVER_NAME=:80
+
+# Se il progetto non usa "public" come document root, impostare questo valore:
+# ENV SERVER_ROOT=web/
+
+# Abilita le impostazioni di produzione di PHP
+RUN mv "$PHP_INI_DIR/php.ini-production" "$PHP_INI_DIR/php.ini"
+
+# Copia i file di PHP del progetto nella cartella public
+COPY . /app/public
+# Se si usa Symfony or Laravel, occorre invece copiare l'intero progetto:
+#COPY . /app
+```
+
+Fare riferimento a "[Creazione di un'immagine Docker personalizzata](docker.md)" per ulteriori dettagli e opzioni,
+e per imparare a personalizzare la configurazione, installare le estensioni PHP e i moduli Caddy.
+
+Se il progetto utilizza Composer,
+assicurarsi di includerlo nell'immagine Docker e di installare le dipendenze.
+
+Quindi, aggiungere un file `compose.yaml`:
+
+```yaml
+# compose.yaml
+services:
+ php:
+ image: dunglas/frankenphp
+ restart: always
+ ports:
+ - "80:80" # HTTP
+ - "443:443" # HTTPS
+ - "443:443/udp" # HTTP/3
+ volumes:
+ - caddy_data:/data
+ - caddy_config:/config
+
+# Volumi necessari per certificati e configurazione di Caddy
+volumes:
+ caddy_data:
+ caddy_config:
+```
+
+> [!NOTE]
+>
+> Gli esempi precedenti sono destinati all'utilizzo in produzione.
+> In fase di sviluppo, si potrebbe voler utilizzare un volume, una diversa configurazione PHP e un valore diverso per la variabile d'ambiente `SERVER_NAME`.
+>
+> Dare un'occhiata al progetto [Symfony Docker](https://github.com/dunglas/symfony-docker)
+> (che utilizza FrankenPHP) per un esempio più avanzato con immagini multi-stage,
+> Composer, estensioni PHP extra, ecc.
+
+Infine, se si usa Git, eseguire il commit e il push di questi file.
+
+## Preparazione del server
+
+Per il deploy dell'applicazione in produzione, è necessario un server.
+In questo tutorial utilizzeremo una macchina virtuale fornita da DigitalOcean, ma qualsiasi server Linux può andar bene.
+Se si ha già un server Linux con Docker installato, passare direttamente a [Configurazione di un nome di dominio](#configuring-a-domain-name).
+
+Altrimenti, utilizzare [questo link di affiliazione di DigitalOcean](https://m.do.co/c/5d8aabe3ab80) per ottenere $ 200 di credito gratuito, creare un account, quindi fare clic su "Cre una Droplet".
+Quindi, fare clic sulla scheda "Marketplace" nella sezione "Scegli un'immagine" e cercare l'app denominata "Docker".
+Ciò fornirà un server Ubuntu con le ultime versioni di Docker e Docker Compose già installate!
+
+A scopo di test, saranno sufficienti i piani più economici.
+Per un utilizzo in produzione reale, probabilmente è meglio scegliere un piano nella sezione "general purpose" adatto alle proprie esigenze.
+
+
+
+Si possono mantenere i valori predefiniti per altre impostazioni o modificarli in base alle proprie esigenze.
+Non dimenticare di aggiungere la chiave SSH o creare una password, quindi premere il pulsante "Finalize and create".
+
+Quindi, attendere qualche secondo mentre il Droplet esegue il provisioning.
+Quando il Droplet è pronto, usare SSH per connettersi:
+
+```console
+ssh root@
+```
+
+## Configurazione di un nome di dominio
+
+Nella maggior parte dei casi, consigliamo di associare un nome di dominio al sito.
+Se non si possiede ancora un nome di dominio, sarà necessario acquistarne uno.
+
+Creare quindi un record DNS di tipo `A` per il nome di dominio che punta all'indirizzo IP del server:
+
+```dns
+your-domain-name.example.com. IN A 207.154.233.113
+```
+
+Esempio con il servizio di domini di DigitalOcean ("Networking" > "Domains"):
+
+
+
+> [!NOTE]
+>
+> Let's Encrypt, il servizio utilizzato per impostazione predefinita da FrankenPHP per generare automaticamente un certificato TLS, non supporta l'utilizzo di indirizzi IP puri. L'utilizzo di un nome di dominio è obbligatorio per utilizzare Let's Encrypt.
+
+## Deploy di FrankenPHP con Docker Compose
+
+Copiare il progetto sul server utilizzando `git clone`, `scp` o qualsiasi altro strumento adatto.
+Se si usa GitHub, è una buona idea usare [una chiave di deploy](https://docs.github.com/en/free-pro-team@latest/developers/overview/managing-deploy-keys#deploy-keys).
+Le chiavi di deploy sono supportate anche da [GitLab](https://docs.gitlab.com/ee/user/project/deploy_keys/).
+
+Esempio con Git:
+
+```console
+git clone git@github.com:/.git
+```
+
+Andare nella cartella contenente il progetto (``) e avviare l'app in modalità produzione:
+
+```console
+docker compose up --wait
+```
+
+Il server è ora attivo e funzionante e un certificato HTTPS è stato generato automaticamente.
+Aprire `https://your-domain-name.example.com` e buon divertimento!
+
+> [!CAUTION]
+>
+> Docker può avere un livello di cache, assicurarsi di avere la build giusta per ogni deploy o ripetere la build del progetto con l'opzione `--no-cache` per evitare problemi di cache.
+
+## Esecuzione dietro un reverse proxy
+
+Se FrankenPHP è in esecuzione dietro a reverse un proxy o un load balancer (ad esempio, Nginx, AWS ELB, Google Cloud LB),
+occorre configurare l'[opzione globale `trusted_proxies`](https://caddyserver.com/docs/caddyfile/options#trusted-proxies) nel Caddyfile
+in modo che Caddy si fidi degli header `X-Forwarded-*` in entrata:
+
+```caddyfile
+{
+ servers {
+ trusted_proxies static
+ }
+}
+```
+
+Se necessario, sostituisre `` con gli intervalli IP effettivi del proxy.
+
+Inoltre, anche il framework PHP usato deve essere configurato per fidarsi del proxy.
+Ad esempio, impostare la [variabile d'ambiente `TRUSTED_PROXIES`](https://symfony.com/doc/current/deployment/proxies.html) per Symfony,
+o il [middleware `trustedproxies`](https://laravel.com/docs/trustedproxy) per Laravel.
+
+Senza entrambe le configurazioni, header come `X-Forwarded-For` e `X-Forwarded-Proto` verranno ignorati,
+il che che potrebbe causare problemi come rilevamento HTTPS errato o indirizzi IP client errati.
+
+## Deploy su più nodi
+
+In caso di deploy su un cluster di macchine, si pèuò utilizzare [Docker Swarm](https://docs.docker.com/engine/swarm/stack-deploy/),
+che è compatibile con i file Compose forniti.
+Per il deploy su Kubernetes, dare un'occhiata al [tabella Helm fornita con API Platform](https://api-platform.com/docs/deployment/kubernetes/), che utilizza FrankenPHP.
diff --git a/docs/it/static.md b/docs/it/static.md
new file mode 100644
index 0000000000..434e7ba0d3
--- /dev/null
+++ b/docs/it/static.md
@@ -0,0 +1,161 @@
+# Creare una build statica
+
+Invece di utilizzare un'installazione locale della libreria PHP,
+è possibile creare una build statica o prevalentemente statica di FrankenPHP grazie al fantastico [progetto static-php-cli](https://github.com/crazywhalecc/static-php-cli) (nonostante il nome, questo progetto supporta tutte le SAPI, non solo la CLI).
+
+Con questo metodo, un unico file binario portatile conterrà l'interprete PHP, il server web Caddy e FrankenPHP!
+
+Gli eseguibili nativi completamente statici non richiedono alcuna dipendenza e possono anche essere eseguiti su un'[immagine Docker `scratch`](https://docs.docker.com/build/building/base-images/#create-a-minimal-base-image-using-scratch).
+Tuttavia, non possono caricare estensioni PHP dinamiche (come Xdebug) e hanno alcune limitazioni, perché utilizzano musl libc.
+
+Per lo più i binari statici richiedono solo `glibc` e possono caricare estensioni dinamiche.
+
+Quando possibile, consigliamo di utilizzare build basate su glibc, per lo più statiche.
+
+FrankenPHP supporta anche [l'incorporamento dell'app PHP nel file binario statico](embed.md).
+
+## Linux
+
+Forniamo immagini Docker per creare binari Linux statici:
+
+### Build basata su Musl, completamente statica
+
+Per un file binario completamente statico che viene eseguito su qualsiasi distribuzione Linux senza dipendenze, ma non supporta il caricamento dinamico delle estensioni:
+
+```console
+docker buildx bake --load static-builder-musl
+docker cp $(docker create --name static-builder-musl dunglas/frankenphp:static-builder-musl):/go/src/app/dist/frankenphp-linux-$(uname -m) frankenphp ; docker rm static-builder-musl
+```
+
+Per prestazioni migliori in scenari fortemente simultanei, si prenda in considerazione l'utilizzo dell'allocatore [mimalloc](https://github.com/microsoft/mimalloc).
+
+```console
+docker buildx bake --load --set static-builder-musl.args.MIMALLOC=1 static-builder-musl
+```
+
+### Build per lo più statica basata su glibc (con supporto per estensioni dinamiche)
+
+Per un binario che supporta il caricamento dinamico delle estensioni PHP, pur mantenendo le estensioni selezionate compilate staticamente:
+
+```console
+docker buildx bake --load static-builder-gnu
+docker cp $(docker create --name static-builder-gnu dunglas/frankenphp:static-builder-gnu):/go/src/app/dist/frankenphp-linux-$(uname -m) frankenphp ; docker rm static-builder-gnu
+```
+
+Questo binario supporta tutte le versioni di glibc 2.17 e successive, ma non funziona su sistemi basati su Musl (come Alpine Linux).
+
+Il file binario risultante, per lo più statico (eccetto `glibc`), è denominato `frankenphp` ed è disponibile nella cartella corrente.
+
+Se vuoi creare il binario statico senza Docker, dai un'occhiata alle istruzioni di macOS, che funzionano anche per Linux.
+
+### Estensioni PHP personalizzate nella build statica
+
+Per impostazione predefinita, vengono compilate le estensioni PHP più popolari.
+
+Per ridurre la dimensione del binario e ridurre la superficie di attacco, è possibile scegliere l'elenco delle estensioni da includere, utilizzando `PHP_EXTENSIONS` come Docker ARG.
+
+Ad esempio, eseguire il comando seguente per creare solo l'estensione `opcache`:
+
+```console
+docker buildx bake --load --set static-builder-musl.args.PHP_EXTENSIONS=opcache,pdo_sqlite static-builder-musl
+# ...
+```
+
+Per aggiungere librerie che abilitano funzionalità aggiuntive alle estensioni abilitate, si può passare `PHP_EXTENSION_LIBS` come Docker ARG:
+
+```console
+docker buildx bake \
+ --load \
+ --set static-builder-musl.args.PHP_EXTENSIONS=gd \
+ --set static-builder-musl.args.PHP_EXTENSION_LIBS=libjpeg,libwebp \
+ static-builder-musl
+```
+
+### Moduli Caddy extra
+
+Per aggiungere moduli Caddy aggiuntivi o passare altri argomenti a [xcaddy](https://github.com/caddyserver/xcaddy), utilizzare `XCADDY_ARGS` Docker ARG:
+
+```console
+docker buildx bake \
+ --load \
+ --set static-builder-musl.args.XCADDY_ARGS="--with github.com/darkweak/souin/plugins/caddy --with github.com/dunglas/caddy-cbrotli --with github.com/dunglas/mercure/caddy --with github.com/dunglas/vulcain/caddy" \
+ static-builder-musl
+```
+
+In questo esempio, aggiungiamo il modulo cache HTTP [Souin](https://souin.io) per Caddy nonché i moduli [cbrotli](https://github.com/dunglas/caddy-cbrotli), [Mercure](https://mercure.rocks) e [Vulcain](https://vulcain.rocks).
+
+> [!TIP]
+>
+> I moduli cbrotli, Mercure e Vulcain sono inclusi per impostazione predefinita se `XCADDY_ARGS` è vuoto o non impostato.
+> Se si personalizza il valore di `XCADDY_ARGS`, vanno inclusi esplicitamente.
+
+Scopri anche come [personalizzare la build statica di FrankenPHP](#customizing-the-frankenphp-static-build)
+
+### Token GitHub
+
+Se si raggiunge il rate limit dell'API GitHub, occorre impostare un token di accesso personale in una variabile di ambiente denominata `GITHUB_TOKEN`:
+
+```console
+GITHUB_TOKEN="xxx" docker --load buildx bake static-builder-musl
+# ...
+```
+
+## macOS
+
+Eseguire il seguente script per creare un file binario statico per macOS (serve [Homebrew](https://brew.sh/) installato):
+
+```console
+git clone https://github.com/php/frankenphp
+cd frankenphp
+./build-static.sh
+```
+
+Nota: questo script funziona anche su Linux (e probabilmente su altri Unix) ed è utilizzato internamente dalle immagini Docker che forniamo.
+
+## Personalizzazione della build statica di FrankenPHP
+
+Le seguenti variabili d'ambiente possono essere passate a `docker build` e a `build-static.sh`
+per personalizzare la build statica:
+
+- `FRANKENPHP_VERSION`: la versione di FrankenPHP da utilizzare
+- `PHP_VERSION`: la versione di PHP da utilizzare
+- `PHP_EXTENSIONS`: le estensioni PHP da compilare ([elenco delle estensioni supportate](https://static-php.dev/en/guide/extensions.html))
+- `PHP_EXTENSION_LIBS`: librerie extra da creare che aggiungono funzionalità alle estensioni
+- `XCADDY_ARGS`: argomenti da passare a [xcaddy](https://github.com/caddyserver/xcaddy), ad esempio per aggiungere moduli Caddy aggiuntivi
+- `EMBED`: percorso dell'applicazione PHP da incorporare nel binario
+- `CLEAN`: quando impostato, libphp e tutte le sue dipendenze vengono create da zero (nessuna cache)
+- `NO_COMPRESS`: non comprimere il file binario risultante utilizzando UPX
+- `DEBUG_SYMBOLS`: quando impostato, i simboli di debug non verranno rimossi e verranno aggiunti al file binario
+- `MIMALLOC`: (sperimentale, solo Linux) sostituisce mallocng di musl con [mimalloc](https://github.com/microsoft/mimalloc) per prestazioni migliorate. Ti consigliamo di utilizzarlo solo per build con targeting Musl, poiché glibc preferisce disabilitare questa opzione e utilizzare invece [`LD_PRELOAD`](https://microsoft.github.io/mimalloc/overrides.html) quando si esegue il codice binario.
+- `RELEASE`: (solo manutentori) quando impostato, il binario risultante verrà caricato su GitHub
+
+## Caricamento dinamico delle estensioni PHP nel file binario statico
+
+Con i binari basati su glibc o macOS, si possono caricare le estensioni PHP in modo dinamico. Tuttavia, queste estensioni dovranno essere compilate con il supporto ZTS.
+Poiché la maggior parte dei gestori di pacchetti attualmente non offre versioni ZTS delle proprie estensioni, andranno compilate a mano.
+
+A tale scopo, è possibile creare ed eseguire il contenitore Docker `static-builder-gnu`, accedervi in remoto e compilare le estensioni con `./configure --with-php-config=/go/src/app/dist/static-php-cli/buildroot/bin/php-config`.
+
+Passaggi di esempio per [l'estensione Xdebug](https://xdebug.org):
+
+```console
+docker build -t gnu-ext -f static-builder-gnu.Dockerfile --build-arg FRANKENPHP_VERSION=1.0 .
+docker create --name static-builder-gnu -it gnu-ext /bin/sh
+docker start static-builder-gnu
+docker exec -it static-builder-gnu /bin/sh
+cd /go/src/app/dist/static-php-cli/buildroot/bin
+git clone https://github.com/xdebug/xdebug.git && cd xdebug
+source scl_source enable devtoolset-10
+../phpize
+./configure --with-php-config=/go/src/app/dist/static-php-cli/buildroot/bin/php-config
+make
+exit
+docker cp static-builder-gnu:/go/src/app/dist/static-php-cli/buildroot/bin/xdebug/modules/xdebug.so xdebug-zts.so
+docker cp static-builder-gnu:/go/src/app/dist/frankenphp-linux-$(uname -m) ./frankenphp
+docker stop static-builder-gnu
+docker rm static-builder-gnu
+docker rmi gnu-ext
+```
+
+Questo creerà `frankenphp` e `xdebug-zts.so` nella cartella corrente.
+Spostando `xdebug-zts.so` nella cartella dell'estensione, aggiungendo `zend_extension=xdebug-zts.so` a php.ini ed eseguendo FrankenPHP, caricherà Xdebug.
diff --git a/docs/it/symfony.md b/docs/it/symfony.md
new file mode 100644
index 0000000000..c941e87f85
--- /dev/null
+++ b/docs/it/symfony.md
@@ -0,0 +1,209 @@
+# Symfony
+
+## Eseguire Symfony con Symfony Docker
+
+Per i progetti [Symfony](https://symfony.com), raccomandiamo l'uso di [Symfony Docker](https://github.com/dunglas/symfony-docker), un progetto ufficiale gestito dall'autore di FrankenPHP. Fornisce una ambiente completo basato du Docker con FrankenPHP, automatizzando HTTPS, HTTP/2, HTTP/3 e supporto ai worker.
+
+## Installare Symfony e FrankenPHP in locale
+
+In alternativa, si possono eseguire progetti Symfony con FrankenPHP da una macchina locale:
+
+1. [Installare FrankenPHP](../#getting-started)
+2. Aggiungere la configuraizone seguente a un file chiamato `Caddyfile` nella cartella principale del progetto Symfony:
+
+ ```caddyfile
+ # Caddyfile
+ # Il dominio del server
+ localhost
+
+ root public/
+ php_server {
+ # Opzionale: abilita la modalità worker per prestazioni migliori
+ worker ./public/index.php
+ }
+ ```
+
+ Si veda la [documentazione sulle prestazioni](performance.md) per altre ottimizzazioni.
+
+3. Lanciare FrankenPHP dalla cartella principale del progetto Symfony: `frankenphp run`
+
+## Modalità worker con Symfony e FrankenPHP
+
+A partire da Symfony 7.4, la modalità worker di FrankenPHP è supportata nativamente.
+
+Per versioni precedenti, installare il pacchetto [PHP Runtime](https://github.com/php-runtime/runtime):
+
+```console
+composer require runtime/frankenphp-symfony
+```
+
+Lanciare il server, definendo la variabile d'ambiente `APP_RUNTIME` per usare il runtime di FrankenPHP in Symfony:
+
+```console
+docker run \
+ -e FRANKENPHP_CONFIG="worker ./public/index.php" \
+ -e APP_RUNTIME=Runtime\\FrankenPhpSymfony\\Runtime \
+ -v $PWD:/app \
+ -p 80:80 -p 443:443 -p 443:443/udp \
+ dunglas/frankenphp
+```
+
+Per approfondire, si veda [la modalità worker](worker.md).
+
+### Verificare la compatibilità dei worker
+
+[Igor PHP](https://github.com/igor-php/igor-php) è un linter statico che analizza progetti Symfony cercando violazioni statiche prima che si verifichino in produzione: servizi senza `ResetInterface`, proprietà con stato che non vengono reimpostate, variabili mutabili locali, chiamate a `exit()` o `die()`, scritture superglobali. Verifica sia il codice dell'applicazione sia i servizi dichiarati in `vendor/`.
+
+```console
+composer require --dev igor-php/igor-php
+vendor/bin/igor-php .
+```
+
+## Ricarica a caldo con Symfony
+
+È abilitato per impostazione predefinita in [Symfony Docker](https://github.com/dunglas/symfony-docker).
+
+Per usare la funzionalità di [ricarca a caldo](hot-reload.md) senza Symfony Docker, abilitare [Mercure](mercure.md) e aggiungere la sotto-direttiva `hot_reload` alla direttiva `php_server` in `Caddyfile`:
+
+```caddyfile
+localhost
+
+mercure {
+ anonymous
+}
+
+root public/
+php_server {
+ hot_reload
+ worker ./public/index.php
+}
+```
+
+Aggiungere quindi il codice seguente al file `templates/base.html.twig`:
+
+```twig
+{# templates/base.html.twig #}
+{% if app.request.server.has('FRANKENPHP_HOT_RELOAD') %}
+
+
+
+{% endif %}
+```
+
+Infine, eseguire `frankenphp run` dalla cartella principale del progetto Symfony.
+
+## Asset pre-compressi
+
+Il componente [AssetMapper](https://symfony.com/doc/current/frontend/asset_mapper.html) può comprimere gli asset con Brotli e Zstandard durante il deploy. FrankenPHP (attraverso `file_server` di Caddy) può servire direttamente questi file compressi direttamente, evitando la complessità di una compressione al volo.
+
+1. Compilare e comprimere gli asset:
+
+ ```console
+ php bin/console asset-map:compile
+ ```
+
+2. Aggiornare `Caddyfile` per servire gli asset compressi:
+
+ ```caddyfile
+ # Caddyfile
+ localhost
+
+ @assets path /assets/*
+ file_server @assets {
+ precompressed zstd br gzip
+ }
+
+ root public/
+ php_server {
+ worker ./public/index.php
+ }
+ ```
+
+La direttiva `precompressed` dice a Caddy di cercare versioni compresse del file richiesto (come `app.css.zst`, `app.css.br`) e li serve direttamente ai client che li supportano.
+
+## Servire grandi file statici (`X-Sendfile`)
+
+FrankenPHP può servire in modo efficiente [grandi file statici](x-sendfile.md) dopo l'esecuzione di codice PHP (per controllo di accessi, statistiche, eccetera).
+
+Symfony HttpFoundation supporta nativamente la [funzionalità](https://symfony.com/doc/current/components/http_foundation.html#serving-files).
+Dopo aver configurato [Caddyfile`](x-sendfile.md#configuring-x-accel-redirect-in-the-frankenphp-caddyfile), troverà automaticamente il valore corretto dell'header `X-Accel-Redirect` da aggiungere alla risposta:
+
+```php
+use Symfony\Component\HttpFoundation\BinaryFileResponse;
+
+BinaryFileResponse::trustXSendfileTypeHeader();
+$response = new BinaryFileResponse(__DIR__.'/../private-files/file.txt');
+
+// ...
+```
+
+## Applicationi Symfony come binari indipendenti
+
+Usando la funzionaltà di [embed di FrankenPHP](embed.md), si possono distribuire applicazioni Symfony
+come binari indipendenti.
+
+Seguire questi passi per preparare e impacchettare l'app Symfony:
+
+1. Preparare l'app:
+
+ ```console
+ # Export the project to get rid of .git/, etc
+ mkdir $TMPDIR/my-prepared-app
+ git archive HEAD | tar -x -C $TMPDIR/my-prepared-app
+ cd $TMPDIR/my-prepared-app
+
+ # Set proper environment variables
+ echo APP_ENV=prod > .env.local
+ echo APP_DEBUG=0 >> .env.local
+
+ # Remove the tests and other unneeded files to save space
+ # Alternatively, add these files with the export-ignore attribute in your .gitattributes file
+ rm -Rf tests/
+
+ # Install the dependencies
+ composer install --ignore-platform-reqs --no-dev -a
+
+ # Optimize .env
+ composer dump-env prod
+ ```
+
+2. Creare un file chiamato `static-build.Dockerfile` nel repository dell'app:
+
+ ```dockerfile
+ # static-build.Dockerfile
+ FROM --platform=linux/amd64 dunglas/frankenphp:static-builder-gnu
+ # If you intend to run the binary on musl-libc systems, use static-builder-musl instead
+
+ # Copy your app
+ WORKDIR /go/src/app/dist/app
+ COPY . .
+
+ # Build the static binary
+ WORKDIR /go/src/app/
+ RUN EMBED=dist/app/ ./build-static.sh
+ ```
+
+ > [!CAUTION]
+ >
+ > Alcuni file `.dockerignore`
+ > ignorano la cartella `vendor/` e i file `.env`. Assicurarsi di modificare o rimuovere il file `.dockerignore` prima della compilazione.
+
+3. Build:
+
+ ```console
+ docker build -t static-symfony-app -f static-build.Dockerfile .
+ ```
+
+4. Estrarre il file binario:
+
+ ```console
+ docker cp $(docker create --name static-symfony-app-tmp static-symfony-app):/go/src/app/dist/frankenphp-linux-x86_64 my-app ; docker rm static-symfony-app-tmp
+ ```
+
+5. Avviare il server:
+
+ ```console
+ ./my-app php-server
+ ```
+
+Ulteriori informazioni sulle opzioni disponibili e su come creare file binari per altri sistemi operativi si possono trovare nella documentazione sull'[embed di applicazioni](embed.md).
diff --git a/docs/it/worker.md b/docs/it/worker.md
new file mode 100644
index 0000000000..7132a8cc3b
--- /dev/null
+++ b/docs/it/worker.md
@@ -0,0 +1,205 @@
+# Utilizzare i worker
+
+Avviare l'applicazione una volta, tenendola in memoria.
+FrankenPHP gestirà le richieste in arrivo in pochi millisecondi.
+
+## Avvio dei worker
+
+### Esecuzione di un worker FrankenPHP con Docker
+
+Impostare il valore della variabile di ambiente `FRANKENPHP_CONFIG` su `worker /path/to/your/worker/script.php`:
+
+```bash
+docker run \
+ -e FRANKENPHP_CONFIG="worker /app/path/to/your/worker/script.php" \
+ -v $PWD:/app \
+ -p 80:80 -p 443:443 -p 443:443/udp \
+ dunglas/frankenphp
+```
+
+### Esecuzione di un worker FrankenPHP con il file binario autonomo
+
+Utilizzare l'opzione `--worker` del comando `php-server` per servire il contenuto della cartella corrente utilizzando un worker:
+
+```bash
+frankenphp php-server --worker /path/to/your/worker/script.php
+```
+
+Se l'app PHP è [incorporata nel file binario](embed.md), si può aggiungere un `Caddyfile` personalizzato nella cartella principale dell'app.
+Verrà utilizzato automaticamente.
+
+È anche possibile [riavviare il worker in caso di modifiche al file](config.md#watching-for-file-changes) con l'opzione `--watch`.
+Il seguente comando attiverà un riavvio se qualsiasi file che termina con `.php` nella cartella o nelle sottocartelle `/path/to/your/app/` viene modificato:
+
+```bash
+frankenphp php-server --worker /path/to/your/worker/script.php --watch="/path/to/your/app/**/*.php"
+```
+
+Questa funzione viene spesso utilizzata in combinazione con [ricaricamento a caldo](hot-reload.md).
+
+## Modalità worker per Symfony
+
+Vedi [la documentazione sulla modalità di lavoro di FrankenPHP Symfony](symfony.md#symfony-worker-mode-with-frankenphp).
+
+## Modalità worker per Laravel Octane
+
+Vedi [la documentazione di FrankenPHP Laravel Octane](laravel.md#laravel-octane).
+
+## Scrittura di un worker personalizzato
+
+L'esempio seguente mostra come creare il proprio worker senza fare affidamento su una libreria di terze parti:
+
+```php
+boot();
+
+// Handler outside the loop for better performance (doing less work)
+$handler = static function () use ($myApp) {
+ try {
+ // Called when a request is received,
+ // superglobals, php://input and the like are reset
+ echo $myApp->handle($_GET, $_POST, $_COOKIE, $_FILES, $_SERVER);
+ } catch (\Throwable $exception) {
+ // `set_exception_handler` is called only when the worker script ends,
+ // which may not be what you expect, so catch and handle exceptions here
+ (new \MyCustomExceptionHandler)->handleException($exception);
+ }
+};
+
+$maxRequests = (int)($_SERVER['MAX_REQUESTS'] ?? 0);
+for ($nbRequests = 0; !$maxRequests || $nbRequests < $maxRequests; ++$nbRequests) {
+ $keepRunning = \frankenphp_handle_request($handler);
+
+ // Do something after sending the HTTP response
+ $myApp->terminate();
+
+ // Call the garbage collector to reduce the chances of it being triggered in the middle of a page generation
+ gc_collect_cycles();
+
+ if (!$keepRunning) break;
+}
+
+// Cleanup
+$myApp->shutdown();
+```
+
+Quindi, avviare l'app e utilizzare la variabile di ambiente `FRANKENPHP_CONFIG` per configurare il worker:
+
+```bash
+docker run \
+ -e FRANKENPHP_CONFIG="worker ./public/index.php" \
+ -v $PWD:/app \
+ -p 80:80 -p 443:443 -p 443:443/udp \
+ dunglas/frankenphp
+```
+
+Per impostazione predefinita, vengono avviati 2 worker per CPU.
+Puoi anche configurare il numero di worker da avviare:
+
+```bash
+docker run \
+ -e FRANKENPHP_CONFIG="worker ./public/index.php 42" \
+ -v $PWD:/app \
+ -p 80:80 -p 443:443 -p 443:443/udp \
+ dunglas/frankenphp
+```
+
+### Riavvia il worker dopo un certo numero di richieste
+
+Poiché PHP non è stato originariamente progettato per processi di lunga durata, ci sono ancora molte librerie e codici legacy che perdono memoria.
+Una soluzione alternativa all'utilizzo di questo tipo di codice in modalità worker consiste nel riavviare lo script worker dopo aver elaborato un certo numero di richieste:
+
+Il precedente frammento di lavoro consente di configurare un numero massimo di richieste da gestire impostando una variabile di ambiente denominata `MAX_REQUESTS`.
+
+### Riavvia i worker manualmente
+
+Sebbene sia possibile riavviare i worker [in seguito alle modifiche dei file](config.md#watching-for-file-changes), è anche possibile riavviare tutti i worker
+tramite l'[API di amministrazione Caddy](https://caddyserver.com/docs/api). Se l'amministratore è abilitato in
+[Caddyfile](config.md#caddyfile-config), si può eseguire il ping dell'endpoint di riavvio con una semplice richiesta POST:
+
+```bash
+curl -X POST http://localhost:2019/frankenphp/workers/restart
+```
+
+### Fallimenti dei worker
+
+Se un worker si blocca con un codice di uscita diverso da zero, FrankenPHP lo riavvierà con una strategia di backoff esponenziale.
+Se lo script worker rimane attivo più a lungo dell'ultimo backoff moltiplicato per due,
+non penalizzerà lo script worker e lo riavvierà di nuovo.
+Tuttavia, se il worker continua a fallire con un codice di uscita diverso da zero in un breve periodo di tempo
+(ad esempio, avendo un errore di battitura in uno script), FrankenPHP si bloccherà con l'errore: `too many consecutive failures`.
+
+Il numero di errori consecutivi può essere configurato nel [Caddyfile](config.md#caddyfile-config) con l'opzione `max_consecutive_failures`:
+
+```caddyfile
+frankenphp {
+ worker {
+ # ...
+ max_consecutive_failures 10
+ }
+}
+```
+
+## Comportamento dei superglobali
+
+[Superglobali PHP](https://www.php.net/manual/en/language.variables.superglobals.php) (`$_SERVER`, `$_ENV`, `$_GET`...)
+comportarsi come segue:
+
+- prima della prima chiamata a `frankenphp_handle_request()`, i superglobali contengono valori legati allo script worker stesso
+- durante e dopo la chiamata a `frankenphp_handle_request()`, i superglobali contengono valori generati dalla richiesta HTTP elaborata, ogni chiamata a `frankenphp_handle_request()` modifica i valori dei superglobali
+
+Per accedere ai superglobali dello script worker all'interno del callback, è necessario copiarli e importare la copia nell'ambito del callback:
+
+```php
+