In quali contesti i plugin sono responsabili della convalida / sanificazione dei dati?


17

Voglio assicurarmi che tutti i dati nei miei plugin / temi siano gestiti in modo sicuro prima di accedere al database e prima di essere inviati al browser. Il mio problema è che ci sono situazioni in cui l'API gestisce la sanificazione per te - come quando si salvano i meta-campi post - e altre in cui l'autore del plugin / tema è interamente responsabile per farlo - come quando si salvano le impostazioni personalizzate.

Ai fini di questa domanda, non sono preoccupato per la convalida dei dati a livello di dominio, ad esempio per verificare che un campo Età su un modulo sia compreso tra 0 e 120 o che un indirizzo e-mail sia valido. Sono preoccupato solo per la sicurezza - ad esempio, evitare le query SQL per evitare l'iniezione di SQL durante il salvataggio nel database o sanificare i dati che vengono generati in modelli HTML per evitare XSS.

Per la sanificazione dell'output, so che è sempre necessario utilizzare funzioni come esc_html()e esc_attr()quando si fa eco alle variabili nei modelli HTML. Ma che dire quando si utilizzano i tag modello ? Disinfettano già tutti l'output? In tal caso, per quale contesto (HTML generale, attributi di tag, ecc.)? Alcune funzioni hanno varianti per contesti diversi (come the_title_attribute(), ma la maggior parte no.

Per la sanificazione dell'input, so che è necessario utilizzare $wpdb->prepare()quando si eseguono query manuali, ma cosa succede quando si utilizza l'API delle impostazioni per creare una pagina delle impostazioni del plug-in o si salvano i metadati post per un tipo di post personalizzato?

In questo momento sto solo scavando attraverso Core e leggendo tutorial ogni volta che uso una funzione per scoprire se disinfetta o no, ma è soggetto a errori e richiede tempo. Spero di trovare una sorta di elenco completo di tutte le possibili situazioni e se l'API lo gestisce o meno. per esempio,

API convalida / sanifica

  • Salvataggio della meta post con update_postmeta()
  • Salvataggio della meta utente con update_user_meta()
  • Emissione del titolo di un post: utilizzare la variante contestualmente appropriata di the_title()
  • eccetera

Devi convalidare / disinfettare manualmente

  • Salvataggio delle opzioni del plug-in con l'API delle impostazioni. Passa una richiamata come terzo parametro di register_setting().
  • Query dirette sul database: avvolgere la query $wpdb->prepare().
  • Emissione di variabili in HTML. Usa esc_attr(), esc_html()ecc
  • eccetera

Sarei anche interessato a capire perché l'API lo fornisce in determinate situazioni, ma non in altre. Suppongo che abbia qualcosa a che fare con la natura sconosciuta dei dati, ma mi piacerebbe sentire una spiegazione approfondita.


Mi piace questa domanda Ho lo stesso pensiero come te. Penso che se ci fosse un tale elenco di quando dobbiamo convalidare / disinfettare manualmente, sarebbe fantastico. +1.
Anh Tran,

1
@Rilwis, per favore vedi la mia risposta. Devi sempre convalidare. La sanificazione è più complicata, in quanto "sicura" dipende dal contesto. In generale, se si utilizza l'API di WordPress con dati noti di WordPress ( the_title(), the_permalink()ecc.), Si sta bene, ma con i dati personalizzati non lo si è (ad es get_post_meta().). In caso di dubbio, disinfetta te stesso - non può far male.
Stephen Harris,

@StephenHarris: ho letto il tuo commento. Lo so anch'io. Ma ho la stessa opinione di Ian Dunn. Penso che il motivo principale che chiede sia "fare abbastanza, niente di più, niente di meno".
Anh Tran,

1
In realtà non mi dispiace sbagliare dal lato della cautela e fare troppe convalide / servizi igienico-sanitari, ma penso che ci siano casi in cui fuggire due volte cose può essere un problema.
Ian Dunn,

Risposte:


15

Ci sono due concetti qui:

  • convalida: assicurarsi che i dati siano validi , ovvero un numero intero è un numero intero, una data è una data (nel formato corretto, ecc.). Questo dovrebbe essere fatto poco prima di salvare i dati.
  • sanificazione : rendere la data sicura per il suo utilizzo nel contesto corrente (ad esempio, escape delle query SQL o escape dell'HTML sull'output).

La convalida dipende quasi universalmente solo da te . Sai quali dati stai chiedendo a un utente e sai quali dati ti aspetti - WordPress no. La convalida verrebbe eseguita, ad esempio, save_postall'hook prima di salvarlo nel database update_post_meta, oppure potrebbe essere fatto specificando una funzione di callback nell'API Impostazioni, chiamata appena prima che WordPress salvi i dati.

La sanificazione è un po 'più mista. Quando si tratta di dati che WordPress conosce nativamente (ad esempio il riquadro di un post), si può essere certi che WordPress ha già reso i dati sicuri. Comunque 'sicuro' dipende dal contesto; ciò che è sicuro per l'uso in una pagina, non è necessariamente sicuro come attributo element. Quindi WordPress avrà funzioni diverse per contesto diverso (ad esempio the_title(), the_title_rss(), the_title_attribute()) - quindi è necessario utilizzare quello giusto .

Per la maggior parte il plug-in potrebbe occuparsi di post meta - o forse dati di eventi da una tabella personalizzata. WordPress non sa cosa sono questi dati o a cosa servono, quindi sicuramente non sa come renderli sicuri. Questo dipende da voi . Ciò è particolarmente importante nell'uso esc_url(), ecc. esc_attr(), esc_textarea()Per impedire che input dannosi siano in grado di incorporare il codice. Poiché WordPress sa che next_posts()si suppone di stampare un url sulla pagina, si applica esc_url()- ma con post meta, diciamo, non sa che memorizza un url - o cosa vuoi fare con esso (se stampa esc_url(), se reindirizza esc_url_raw(). Se in dobut - errare con cautela e scappare da soli - e farlo il più tardi possibile.

Infine, che dire del salvataggio dei dati? Devi renderlo sicuro allora? Come accennato si fa necessità di assicurarsi dati sono validi. Ma se si utilizza l'API di WordPress ( wp_insert_post(), update_post_meta()ecc.), Non è necessario disinfettare i dati, poiché quando si salvano i dati l'unica sanificazione che è necessario eseguire è quella di sfuggire alle istruzioni SQL e WordPress lo fa. Se si eseguono istruzioni SQL dirette (ad esempio per leggere / scrivere dati da una tabella personalizzata), è necessario utilizzare la $wpdbclasse per facilitare la sanificazione delle query.

Ho scritto questo post sul blog sulla sanificazione e la convalida dei dati che potresti trovare utile - in esso parlo di cosa ci si aspetta da te al riguardo.


Ehi Stephan, grazie per la spiegazione. Questo mi ha aiutato a capirlo un po 'meglio, ma quello che sto davvero cercando è una specie di elenco completo, come nell'esempio che ho dato. Sembra che il tuo approccio sia quello di fare un'ipotesi istruita se WP lo gestisce o di sbagliare sul lato della cautela e sempre igienizzare. Mi sentirei più sicuro se avessi un elenco autorevole e completo, piuttosto che fare affidamento sulla mia comprensione di esso. Sono anche preoccupato che la doppia fuga possa portare a problemi.
Ian Dunn,

Ho anche appena aggiornato la domanda per chiarire alcune cose.
Ian Dunn,

0

Non sono sicuro che sia completo, ma con qualsiasi plug-in o tema, l'input dell'utente dovrebbe essere disinfettato. Le operazioni del database devono essere eseguite utilizzando i metodi $ wpdb->. Tutti i dati $ _GET e $ _POST devono essere disinfettati.

Questa è la migliore pratica per la programmazione PHP di WordPress.

Quindi, in conclusione, se esiste una funzione WordPress, usala, in caso contrario, disinfetta le tue variabili e inserisci te stesso.

Se fossi troppo vago, per favore fai una domanda più specifica.


3
Capisco che deve sempre essere disinfettato, ma la domanda riguarda chi esegue la sanificazione in ogni situazione particolare. A volte WordPress lo fa automaticamente, a volte devi farlo manualmente. Ho aggiornato la domanda per provare a renderlo più chiaro.
Ian Dunn,

Anche quando si utilizza update_user_meta (), è comunque necessario convalidarlo, poiché i valori aggiornati potrebbero provenire da un modulo esposto o dall'input di un utente. Se è un valore proveniente da uno script, come una decisione interna, da un ciclo if / else, non dovresti disinfettarlo.
Ciprian,

1
Il valore si passa a update_user_meta()viene passato attraverso stripslashes_deep()e sanitize_meta()in update_metadata(), e poi $wpdb->prepare()in $wpdb->update(). Quindi, non penso che tu abbia bisogno di disinfettarlo. Mi sto perdendo qualcosa?
Ian Dunn,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.