Configurazione tipica di $allowed in wp_kses
Ho una casella di testo personalizzata per i post e vorrei sanitizzarla usando wp_kses
prima di aggiornare la meta del post.
Stavo cercando esempi di configurazioni comuni per $allowed
, ma ho trovato solo questo esempio:
$allowed = array(
'a' => array( // permette solo i tag a
'href' => array() // e questi anchor possono avere solo l'attributo href
)
);
Qual è una configurazione tipica per wp_kses
con $allowed
? Qualcuno può fornire un esempio di ciò che normalmente si filtra?

Non concordo con la soluzione proposta da @JaredCobb, wp_kses()
è molto più flessibile del metodo da lui presentato. Può rimuovere attributi indesiderati dai tag senza distruggere i tag stessi. Ad esempio, se l'utente inserisce <strong class='foo'>
, wp_kses()
restituirebbe <strong>
se non si permette l'attributo class, mentre strip_tags()
rimuoverebbe completamente il tag <strong>
.
@redconservatory: Gli attributi che vorrai utilizzare sono i seguenti:
$args = array(
//formattazione
'strong' => array(),
'em' => array(),
'b' => array(),
'i' => array(),
//link
'a' => array(
'href' => array()
)
);
Questo permetterà grassetti e corsivi senza attributi, così come tag anchor con attributo href
... e nient'altro. Utilizza il principio della whitelist, che come giustamente notato da @jaredcobb è l'approccio migliore in questo caso.

Non puoi specificare a strip_tags quali tag sono consentiti? http://php.net/manual/en/function.strip-tags.php

Anche se, ora posso capire meglio perché wp_kses è superiore, visto che vedo come rimuove le classi indesiderate...

Probabilmente non mi sono spiegato chiaramente... Ma sì, wp_kses
offre un controllo maggiore rispetto alle opzioni native di PHP. Penso di averlo detto. Ho usato anche la parola "attributi". Stavo dicendo che dipende dal tuo caso d'uso. Qualcuno che cerca di proteggere i propri dati da tutti i tag sarebbe meglio se usasse strip_tags secondo me, ma è più una mia preferenza che altro. Saluti.

Inizierei con lo stesso array $allowedtags
che WordPress utilizza per i commenti. Puoi trovare il loro array nel file [directory wordpress]/wp-includes/kses.php
. Questi sembrano valori predefiniti ragionevoli e un buon punto di partenza. Ecco il loro array...
$allowedtags = array(
'a' => array(
'href' => true,
'title' => true,
),
'abbr' => array(
'title' => true,
),
'acronym' => array(
'title' => true,
),
'b' => array(),
'blockquote' => array(
'cite' => true,
),
'cite' => array(),
'code' => array(),
'del' => array(
'datetime' => true,
),
'em' => array(),
'i' => array(),
'q' => array(
'cite' => true,
),
'strike' => array(),
'strong' => array(),
);
NON userei la funzione PHP strip_tags
come sostituto di wp_kses
.
Non dovresti mai usare strip_tags per filtrare contenuti di utenti sconosciuti!
Ho creato un video veloce che spiega Perché wp_kses() di WordPress è meglio di strip_tags() di PHP per la sicurezza.

Ecco qui. Questo funziona sia in WordPress che al di fuori di WordPress.
<?php
$str = ' I am <strong>stronger</strong> and cooler every single day <aaaaa>. ';
echo orbisius_html_util::strip_tags($str);
/**
* Classe di utilità HTML
* @author Svetoslav Marinov (SLAVI) | http://orbisius.com
*/
class orbisius_html_util {
/**
* Utilizza wp_kses di WP per pulire alcuni tag html ma consente alcuni attributi
* utilizzo: orbisius_html_util::strip_tags($str);
* utilizza wp_kses() di WordPress
* @param str $buffer stringa buffer
* @return str testo ripulito
*/
public static function strip_tags($buffer) {
static $default_attribs = array(
'id' => array(),
'class' => array(),
'title' => array(),
'style' => array(),
'data' => array(),
'data-mce-id' => array(),
'data-mce-style' => array(),
'data-mce-bogus' => array(),
);
$allowed_tags = array(
'div' => $default_attribs,
'span' => $default_attribs,
'p' => $default_attribs,
'a' => array_merge( $default_attribs, array(
'href' => array(),
'target' => array('_blank', '_top'),
) ),
'u' => $default_attribs,
'i' => $default_attribs,
'q' => $default_attribs,
'b' => $default_attribs,
'ul' => $default_attribs,
'ol' => $default_attribs,
'li' => $default_attribs,
'br' => $default_attribs,
'hr' => $default_attribs,
'strong' => $default_attribs,
'blockquote' => $default_attribs,
'del' => $default_attribs,
'strike' => $default_attribs,
'em' => $default_attribs,
'code' => $default_attribs,
);
if (function_exists('wp_kses')) { // WP è presente
$buffer = wp_kses($buffer, $allowed_tags);
} else {
$tags = array();
foreach (array_keys($allowed_tags) as $tag) {
$tags[] = "<$tag>";
}
$buffer = strip_tags($buffer, join('', $tags));
}
$buffer = trim($buffer);
return $buffer;
}
}

Ciao, Signor Svetoslav, questo è ancora sicuro al giorno d'oggi? Stavo cercando un modo semplice ma sicuro per sanificare l'input utente nel mio backoffice (non Wordpress). Vorrei solo permettere l'uso di formattazione HTML di base come quella presente nel tuo codice, <b>, <i>, <u>. Pensi che possa usare strip_tags($_POST['myDoc']) o dovrei fare altro per essere sicuro? Grazie per l'aiuto!

Ciao, usa il mio codice. Verifica se è eseguito in un contesto WordPress e utilizzerà la funzione di WP, altrimenti ricadrà su strip_tags di PHP. Inoltre è meglio usare $_REQUEST piuttosto che $_POST perché a un certo punto potresti passare dati come parametro GET.

grazie per la risposta :-). Sto avendo un problema ora... se incollo HTML formattato o per esempio del codice da Sublime Text 3, gran parte del testo scompare, ci deve essere del codice formattato nascosto che interrompe lo script.

Potrebbe essere, sto ripulendo l'html come ho scritto nella risposta sopra, cercando \n, \r e così via ma il problema persiste :-(. Pulire i dati incollati può essere un grosso problema, alcuni anni fa usavo copia e incolla su textedit per ripulire le stringhe copiate, ma non posso aspettarmi che i miei utenti facciano lo stesso.

Ho utilizzato wp_kses
solo quando avevo la necessità specifica di consentire/filtrare attributi di tag HTML (ad esempio, voglio permettere che abbiano un tag <image>
con un attributo src=""
ma non voglio che possano inserire href=""
o style=""
o qualsiasi altro attributo nel tag immagine. In quel caso, wp_kses
è utile perché (come puoi vedere nell'esempio che hai creato) puoi filtrare in modo molto specifico. Tuttavia, ho usato raramente wp_kses
perché trovo che un paio di funzioni native di PHP (di seguito) facciano il lavoro e siano più facili da capire quando rivedo il codice dopo diversi mesi.
Se vuoi rimuovere completamente i tag HTML (tranne magari consentirne alcuni), uso sempre strip_tags
. Puoi passare una stringa di tag consentiti (come <p> <br> <strong>
) o qualsiasi altro tag innocuo che preferisci. Questo permette all'utente di avere un certo controllo sulla formattazione, se è applicabile al tuo caso d'uso. Mi piace strip_tags
perché adotta un approccio di whitelist per sanificare i dati. (Significa che tutto viene rimosso tranne ciò che esplicitamente whitelisti).
Se il tuo obiettivo è permettere loro di inserire qualsiasi HTML nel contenuto, ma vuoi solo mostrare il loro testo così come l'hanno inserito (come esempi di codice), usa htmlspecialchars
. Questo convertirà i caratteri HTML nelle loro controparti codificate in modo da poterli visualizzare in sicurezza nella pagina.
Potresti imbatterti in codice che usa str_replace
che "cerca" tag cattivi come <script> o <iframe> o qualsiasi altro. Non raccomando affatto questo approccio perché adotta una blacklist per sanificare i dati e devi costantemente assicurarti che la tua blacklist sia aggiornata.
Per riassumere, dipende dallo scopo delle tue metabox. Se stai proteggendo contro input da parte di utenti (che potrebbero essere malintenzionati), consiglio strip_tags
e di consentire solo alcuni tag innocui. Se hai una buona ragione per gestire in modo molto dettagliato i tag e gli attributi specifici del contenuto dell'utente, usa wp_kses
.

wp_kses()
non fa tutto quello che fa strip_tags()
e anche di più? Sono assolutamente d'accordo nel mantenere le cose semplici, ma penso anche che ci sia un argomento a favore di non "sorprendere" nessuno. wp_kses()
è "il modo di WordPress", e visto che stiamo scrivendo codice WordPress, c'è da dire che probabilmente è la scelta migliore. Inoltre, se in futuro volessimo permettere certe combinazioni di tag/attributi, usare wp_kses()
fin dall'inizio non richiederebbe un refactoring.

Puoi anche utilizzare la funzione wp_kses_post che viene usata per il contenuto dei post e richiede solo i dati come parametro.
Maggiori informazioni qui: http://codex.wordpress.org/Function_Reference/wp_kses_post

@Svetoslav Marinov
Ho aggiunto questo codice subito dopo $buffer = trim($buffer);
$string_limpa = array(
'<div><p><\/div>' => '<br>',
'<div><br><\/div>'=> '<br>',
'<div align="left"><br><\/div>' => '<br>',
'<div align="center"><br><\/div>' => '<br>',
'<div align="right"><br><\/div>' => '<br>',
'<div style="text-align: left;"><br><\/div>' => '<br>',
'<div style="text-align: center;"><br><\/div>' => '<br>',
'<div style="text-align: right;"><br><\/div>' => '<br>',
'<div style="text-align: justify;"><br><\/div>' => '<br>',
'class="Apple-style-span"' => '<br>',
'<p><br></p>' => '<br>',
'<p><b></p>' => '<br>',
'<p><i></p>' => '<br>',
'<p><u></p>' => '<br>',
'\r' => '<br>',
'\n' => '<br>',
'\t' => ' ',
'\0' => ' ',
'\x0B' => '<br>',
'<p style="text-align: center;"><br></p>' => '<br>'
);
return strtr($buffer, $string_limpa);
per provare a pulire l'html ed evitare che caratteri nascosti incollati rompano il codice, ma non funziona, pulisce l'html, ma i caratteri nascosti rimangono comunque.
