React
Sanitizzare l'input contro XSS: cosa serve
L'input non si sanifica in ingresso: si codifica in uscita e solo l'HTML generato dagli utenti passa da un sanitizer come DOMPurify.
In sintesi
- L'input si codifica in uscita; solo l'HTML generato dagli utenti va sanificato.
- React sfugge il testo in JSX, non il markup passato a dangerouslySetInnerHTML.
- La sanificazione va ripetuta sul server: il client si può modificare.
L'input non si sanifica in ingresso: si codifica in uscita, e solo l'HTML generato dagli utenti passa da un sanitizer come DOMPurify.
Il testo non è il pericolo
React, distribuito con licenza MIT, sfugge già i valori: {commento} finisce nel DOM come testo, non come markup. Il buco si apre con dangerouslySetInnerHTML, dove la stringa arriva al DOM così com'è.
Codificare o sanificare
function Commento({ testo }) {
return {testo}; // React escapes the string, no script runs
}
function CommentoRicco({ html }) {
return ;
}
La prima versione è sicura per costruzione: il testo resta testo. La seconda accetta markup, quindi deve passare da DOMPurify, disponibile con licenza Apache-2.0 o MPL-2.0, prima di toccare il DOM.
Le regole che reggono
- Codifica in uscita: il testo diventa entità quando entra nel DOM, non quando arriva dal form.
- Sanifica solo l'HTML: un editor ricco ha bisogno di un parser che rimuova tag, attributi e URL con schema
javascript:. - Niente concatenazione: comporre HTML con
+salta ogni difesa, anche quando i pezzi sembrano innocui.
Installazione
npm i dompurify
Il pacchetto non chiede configurazione: DOMPurify.sanitize usa una lista di tag ammessi, e la si restringe con ALLOWED_TAGS quando il contenuto deve restare semplice.
Record vivi nel catalogo
Tre componenti dove l'input dell'utente conta: interfaces-textarea, link-preview e input. Per sfogliare per categoria parti da 111.985 componenti.
La limitazione
La sanificazione nel browser non basta se l'HTML viene salvato e servito ad altri: un client modificato può inviare markup non filtrato. La stessa funzione va eseguita sul server, dove DOMPurify richiede jsdom come DOM.
Dove continuare
Il modello dei campi è in form controllati e non; il flusso progressivo è in form progressivo con Next.js; la differenza fra azioni server e API è in Server Actions vs API.
Domande frequenti
Basta React per evitare XSS?
Per il testo sì: JSX sfugge i valori. Per l'HTML no: dangerouslySetInnerHTML lo inserisce così com'è e serve un sanitizer.
Posso sanificare con una regex?
No. Una regex non conosce la grammatica HTML e lascia passare varianti come attributi spezzati o entità annidate. Serve un parser.
Dove va applicata la sanificazione?
In uscita, nel punto in cui l'HTML entra nel DOM. Va ripetuta sul server, perché il client può essere modificato.
DOMPurify funziona anche in Node?
Sì, con jsdom a fornire il DOM. Nel browser usa quello nativo. La licenza è Apache-2.0 o MPL-2.0.
Un nome o un'email vanno sanificati?
No. Vanno validati e codificati in uscita: non sono HTML e non devono diventarlo.