Funzione PHP flush(): Inviare l'Output al Browser Immediatamente
Scopri come PHP flush() invia l'output bufferizzato al browser subito, le differenze da ob_flush() e quando usarla negli script di lunga durata.
Per impostazione predefinita, PHP raccoglie il testo prodotto dallo script (con echo, print, ecc.) e lo invia al browser a blocchi — spesso solo al termine dello script. La funzione integrata flush() permette di trasmettere immediatamente tutto ciò che è già stato prodotto in questo momento, così l'utente vede un output parziale prima che la pagina sia completamente generata. Questa pagina spiega cosa fa flush(), come si differenzia da ob_flush(), i buffer che si frappongono tra lo script e il browser, e quando ricorrervi è davvero utile.
Cosa Fa la Funzione flush()
flush(): voidflush() chiede a PHP di consegnare qualsiasi output che sta trattenendo al livello sottostante — il SAPI e il server web. Non accetta argomenti e non restituisce nulla. Un uso comune è negli script di lunga durata che devono mostrare lo stato di avanzamento (una riga di log, un contatore) invece di lasciare l'utente a fissare una pagina bianca finché tutto non è terminato.
Due limiti importanti:
flush()non agisce sul livello di output buffering di PHP (quello avviato conob_start()). Se l'output buffering è attivo, il testo rimane intrappolato nel buffer di PHP eflush()non ha nulla da inviare. È necessario rilasciare prima quel livello conob_flush()oob_end_flush().flush()non può ignorare il buffering effettuato dal server web o dal proxy (Apachemod_deflate, Nginxproxy_buffering, FastCGI, gzip). Questi possono comunque trattenere i dati finché non decidono di inviarli.
Un Esempio di Base
Quando nessun output buffering PHP è attivo, flush() da solo è sufficiente per trasmettere l'output corrente:
<?php
echo "Starting a slow task...\n";
flush(); // send the line above to the browser now
sleep(2); // pretend we are doing real work
echo "Done!\n";
?>Senza la chiamata a flush(), l'utente vedrebbe tipicamente entrambe le righe comparire insieme dopo 2 secondi. Con essa, "Starting a slow task..." può arrivare immediatamente.
flush() vs ob_flush()
Questa è la distinzione che crea più confusione. PHP può impilare due buffer separati, e ciascuna funzione *flush ne riguarda uno diverso:
| Funzione | Buffer che svuota |
|---|---|
ob_flush() | Il buffer di output-control di PHP (creato da ob_start()) → sposta i dati nel buffer SAPI |
flush() | Il buffer SAPI / write → sposta i dati verso il browser |
Quando l'output buffering è attivo, sono necessarie entrambe, nell'ordine corretto — prima ob_flush() per rilasciare il buffer di PHP, poi flush() per trasmetterlo:
<?php
ob_start(); // turn on PHP output buffering
echo "Buffered text\n";
ob_flush(); // PHP buffer -> SAPI buffer
flush(); // SAPI buffer -> browser
?>Invertire l'ordine o omettere ob_flush() fa sì che il testo rimanga bloccato in PHP. Se si vuole che PHP esegua il flush dopo ogni echo automaticamente, vedere ob_implicit_flush().
Perché Spesso "Non Funziona"
Trasmettere l'output in modo affidabile è più difficile che chiamare una sola funzione, perché diversi livelli effettuano il buffering in modo indipendente:
- gzip / compressione —
zlib.output_compressionemod_deflatedi Apache devono accumulare un numero sufficiente di byte prima di inviare. Disabilitare la compressione per la risposta che si vuole trasmettere in streaming. - Buffering del server web / proxy — Nginx (
proxy_buffering on), FastCGI e i load balancer spesso effettuano un re-buffer della risposta. - Rendering del browser — alcuni browser attendono un numero minimo di byte prima di eseguire il rendering; aggiungere padding all'output può forzare un rendering anticipato.
Per queste ragioni, flush() va trattata come un suggerimento, non una garanzia. Per esigenze moderne di streaming (server-sent events, API chunked) è preferibile configurare esplicitamente il server anziché affidarsi solo a flush().
Funzioni di Output Correlate
ob_flush()— svuota il buffer di output-control di PHP.ob_end_flush()— svuota il buffer e disattiva l'output buffering.ob_get_flush()— restituisce il contenuto del buffer e lo svuota.- PHP Output Control — panoramica di come i livelli di buffering si relazionano tra loro.
fflush()— svuota le scritture bufferizzate su un file aperto (non sul browser).
Conclusione
flush() forza PHP a inviare l'output già prodotto verso il browser invece di attendere la fine dello script. Tenere a mente che agisce solo sul buffer SAPI/write: con ob_start() attivo è necessario chiamare prima ob_flush(), e anche in quel caso il server web o il livello di compressione possono ritardare la consegna. Usata con questa consapevolezza, flush() è un metodo pratico per trasmettere in streaming l'avanzamento degli script di lunga durata.