$_GET è un array con la query string dell'URL, quindi article.php?id=42&lang=en dà $_GET['id'] === '42' e $_GET['lang'] === 'en'. $_POST è un array con i campi di un form inviato con method="post". Leggili entrambi con un default, $_GET['id'] ?? null, perché la chiave manca ogni volta che manca il parametro.
Esegui il blocco, poi clicca i link: ogni clic esegue di nuovo lo script con $_GET compilato dalla query string del link.
$_GET['lang'] è ciò che dice l'URL, non solo i tre link che hai stampato. Chiunque può scrivere ?lang=<script> nella barra degli indirizzi, ed è per questo che il blocco cerca il valore in $languages invece di stamparlo, e applica l'escape nell'unico punto in cui stampa dati della richiesta.
Leggere un numero dalla query string
Ogni valore in $_GET è una stringa. Per un numero di pagina, valida e converti in un solo passo con filter_var() e ripiega su un default quando il valore manca, non è un numero o è fuori intervallo. Scorri le pagine, poi prova i link Page 999 e Page abc.
filter_var() restituisce l'intero 3 per "3" e l'opzione default per qualsiasi altra stringa, quindi $page è sempre un int utilizzabile. La pagina su filter_var elenca gli altri validatori.
Leggere i dati di un form con $_POST
Un form con method="post" invia i suoi campi nel corpo della richiesta, e PHP li mette in $_POST sotto il name di ogni input. $_SERVER['REQUEST_METHOD'] ti dice se la richiesta corrente è la prima visita (GET) o un invio (POST). Compila il form e premi Send per vederli entrambi.
Un input di testo vuoto viene comunque inviato, come "", quindi dopo un invio $_POST['title'] esiste anche se il visitatore non ha scritto nulla. Su un server REQUEST_METHOD è sempre impostato; il ?? 'GET' serve solo a non far protestare lo script quando esegui il file con php dalla riga di comando. Lo schema completo per validare e mostrare di nuovo un form è nella pagina sui form.
Un form di ricerca con method="get"
Usa GET per un form il cui risultato deve essere un URL condivisibile, come una casella di ricerca. Il browser trasforma i campi in una query string (?q=sort&level=beginner) e lo script li legge da $_GET, esattamente come un link. Cerca array o string.
Costruire link con http_build_query
Scrivere "?q=$q&page=2" a mano si rompe appena $q contiene uno spazio, & o #. http_build_query() codifica ogni valore per te, e il risultato passa per htmlspecialchars() quando finisce in un href, perché dentro l'HTML & dovrebbe essere &.
parse_str() con due argomenti è il modo in cui PHP costruisce $_GET da una query string, quindi è comodo per i test. Passa sempre il secondo argomento; la vecchia forma con un solo argomento, che creava variabili, è stata rimossa in PHP 8.
$_REQUEST e perché evitarlo
$_REQUEST è $_GET e $_POST uniti in un solo array. I file php.ini distribuiti con PHP impostano request_order = "GP", quindi quando entrambi contengono la stessa chiave vince POST; senza quell'impostazione vengono uniti anche i cookie:
<?php
// POST /save.php?id=1 with a form field id=2
echo $_GET['id']; // "1"
echo $_POST['id']; // "2"
echo $_REQUEST['id']; // "2"
Sembra comodo, ma nasconde da dove arriva un valore. Un gestore che elimina un record in base a $_REQUEST['id'] può essere attivato da un semplice link, ed è esattamente ciò che le azioni solo POST devono impedire. Leggi invece $_GET o $_POST per nome.
GET vs POST: quale usare
| GET | POST | |
|---|---|---|
| Dove viaggiano i dati | Nell'URL: ?q=php&page=2 | Nel corpo della richiesta |
| Si leggono con | $_GET | $_POST |
| Preferiti, condivisione, tasto indietro | Sì | No (il browser chiede di reinviare) |
| Lunghezza | Limitata dall'URL (qualche migliaio di caratteri è sicuro) | Limitata da post_max_size (8M di default) |
| Upload di file | No | Sì, con enctype="multipart/form-data" (leggi $_FILES) |
| Usalo per | Ricerca, filtri, ordinamento, paginazione | Accesso, registrazione, salvare, eliminare, pagamenti |
La regola che conta: una richiesta GET non deve modificare nulla. I browser precaricano i link, i crawler li seguono e le persone li condividono, quindi prima o poi un link ?delete=5 verrà seguito da qualcosa che non doveva eliminare nulla. Nessuno dei due metodi è cifrato di per sé: HTTPS protegge entrambi, e POST tiene solo i dati fuori dall'URL, dalla cronologia del browser e dai log del server.
Domande frequenti
Come ottengo un parametro dall'URL in PHP?
Leggilo da $_GET con un default: per page.php?id=42, $id = $_GET['id'] ?? null; dà la stringa "42". Ogni valore è una stringa (o un array per id[]=), quindi convertilo e validalo, per esempio con filter_var($id, FILTER_VALIDATE_INT).
Qual è la differenza tra $_GET e $_POST?
$_GET arriva dalla query string dell'URL, quindi è visibile, si può salvare nei preferiti ed è limitato in lunghezza; usalo per ricerche, filtri e pagine. $_POST arriva dal corpo della richiesta di un form inviato con method="post"; usalo per tutto ciò che modifica dati, come salvare, acquistare o accedere.
Come verifico se un parametro GET esiste in PHP?
Usa isset($_GET['q']), che è falso quando la chiave manca o è null. Per trattare come mancante anche un valore vuoto (?q=), confronta il valore dopo il trim: trim($_GET['q'] ?? '') !== ''.
Conviene usare $_REQUEST in PHP?
Di solito no. $_REQUEST unisce $_GET e $_POST (e, a seconda di request_order, i cookie), quindi non puoi sapere da dove arriva un valore, e un link può fornire un valore che ti aspettavi da un form. Leggi esplicitamente $_GET o $_POST.
Come verifico se una richiesta è GET o POST in PHP?
Confronta $_SERVER['REQUEST_METHOD']: if ($_SERVER['REQUEST_METHOD'] === 'POST') { ... }. È più affidabile di isset($_POST['submit']), che fallisce quando il pulsante non ha un name o quando il form viene inviato da JavaScript o da un altro script senza quel campo.