> Manuales > Taller de PHP

Cómo procesar código HTML desde aplicaciones PHP, para eliminar posibles ataques XSS y restringir las etiquetas utilizadas, con la librería HTML Purifier, que se utiliza para filtrar validar y depurar código HTML.

Esta librería permite eliminar código malicioso (XSS) y validar las etiquetas HTML que queramos definir como permitidas. También valida el código HTML con el estándar que nosotros deseemos y realiza las modificaciones necesarias para "purificarlo".

HTML Purifier es gratuito y de código libre. Se trata además de un sistema altamente personalizable que puede abarcar varios tipos de usos dentro de un sitio web. Se utiliza generalmente para validar los campos que se reciben desde editores WYSIWYG o simplemente para validar el código que se muestra en una página web.

Toda la documentación, archivos de descarga y ejemplos los puedes encontrar en http://htmlpurifier.org . El sitio web de la librería está bastante completo y tiene varios textos con documentación y demos que sirven para hacerse una idea de las posibilidades y sobre cómo programar el script PHP para configurar la librería de filtrado de HTML.

Existen otras librerías similares para filtrar, validar y depurar HTML, con distintas funcionalidades y complejidades. Alguna de ellas ya las habíamos comentado en DesarrolloWeb.com, como la librería Kses, que es bastante más sencilla en sus posibilidades, pero también un poco más fácil de utilizar. HTML Purifier es quizás el filtro de HTML más completo y para comprobarlo podemos acceder a una comparativa de distintos filtros que aparece en la propia página del HTML Purifier. Claro que es una comparativa un poco subjetiva, que intenta ensalzar las posibilidades de su propia librería, pero aun así merece la pena echarle un vistazo para y conocer el verdadero alcance de HTML Purifier.

Instalación de HTML Purifier

Primero convendría saber que la última versión de HTML Purifier sólo es compatible con PHP 5. Es el único requisito importante de conocer antes de decantarnos por esta solición.

Hay dos versiones para descargar esta librería desde http://htmlpurifier.org/download. La única diferencia entre la versión completa y la "Lite" es que se ha eliminado la documentación, los archivos de prueba, perfiles y archivos de mantenimiento, es decir, sólo contiene la carpeta con la librería.

Una vez descargado, descomprimimos el archivo y lo guardamos en el servidor. Después hay que darle permisos de escritura a la carpeta HTMLPurifier/DefinitionCache/Serializer. Suponiendo que hemos descomprimido el archivo en la carpeta raíz del servidor, hay que incluir unas líneas de código en el archivo donde vamos a utilizar esta librería:

Ejemplo de HTML Purifier

Vamos a mostrar un ejemplo utilizando algunas de las funciones de filtrado de HTML, que proporciona la librería y que permiten verificar un código HTML.

En el ejemplo partiremos de un código HTML inicial en el que contendrá una serie de etiquetas HTML, de las cuales, las que nosotros no indiquemos como válidas, las eliminará de nuestro código.

En el siguiente código tenemos una cadena de caracteres con una serie de etiquetas HTML. Lo utilizaremos para configurar HTML Purifier de modo que elimine las etiquetas no permitidas.

$miHTML='<strong>Prueba de HTML Purifier de <a target="_blank" href="www.desarrolloweb.com">www.desarrolloweb.com</a></strong>';

Primero configuramos incluimos la librería y la configuramos con la codificación que necesitemos.

$config = HTMLPurifier_Config::createDefault();
$config->set('Core.Encoding', 'ISO-8859-1');

Indicaremos, de manera opcional, que automáticamente ponga saltos de linea al código que queremos verificar. Esto hace que los saltos de línea dobles se cambien por etiquetas P. Los saltos de línea los deja tal cual. Y por supuesto, para que funcione tenemos que incluir a la etiqueta P entre las permitidas. Luego veremos cómo hacerlo.

$config->set('AutoFormat.AutoParagraph', true);

Después indicaremos las etiquetas y atributos permitidos para nuestro código HTML. En nuestro ejemplo, vamos a permitir las etiquetas “b”, “p”, “div” y “a”, de las cuales de la etiqueta “p” sólo admitirá el atributo “align” y de la etiqueta “a” admitirá los atributos “target” y “href”. El resto de las etiquetas permitidas admiten todos sus atributos correspondientes.

$config->set('HTML.Allowed', 'b,p[align],div,a[target|href]');

Si queremos que en una etiqueta en concreto sólo se pueda admitir un cierto valor de un atributo, incluiremos el siguiente código indicando el archivo desde donde se está ejecutando este código. Hay que crear una nueva directiva de HTMLDefinicion con un identificador único de la definición.

$config->set('HTML.DefinitionID', '1');

Y hay que crear también un identificador exclusivo para la definición anterior, que sirve para manejar la caché de manera inteligente y a la vez vaciarla.

$config->set('HTML.DefinitionRev', 1);
$def = $config->getHTMLDefinition(true);

Aquí hemos indicado que para la etiqueta “a” sólo admita el atributo “target” con el valor “_blank”. Dentro del array se pueden indicar todos los valores que queramos que pueda tomar el atributo de la etiqueta en concreto.

$def->addAttribute('a', 'target', new HTMLPurifier_AttrDef_Enum(
array('_blank')
));

Y ya sólo queda purificar nuestro código HTML.

$purifier = new HTMLPurifier($config);
$html_purificado = $purifier->purify($miHTML);

Puedes ver mas funcionalidades de esta librería en la documentación de HTML purifier http://htmlpurifier.org/docs

Para terminar vamos a mostrar el código del ejemplo completo.

$miHTML='<strong>Prueba de HTML Purifier de <a target="_blank" href="https://desarrolloweb.com">www.desarrolloweb.com</a></strong>';

$config = HTMLPurifier_Config::createDefault();
$config->set('Core.Encoding', 'ISO-8859-1');
$config->set('AutoFormat.AutoParagraph', true);
$config->set('HTML.Allowed', 'b,p[align],div,a[target|href]');
$config->set('HTML.DefinitionID', '1');
$config->set('HTML.DefinitionRev', '1');
$def = $config->getHTMLDefinition(true);
$def->addAttribute('a', 'target', new HTMLPurifier_AttrDef_Enum(
array('_blank')
));

$purifier = new HTMLPurifier($config);
$html_purificado = $purifier->purify($miHTML);

Gema Maria Molina Prados

Equipo DesarrolloWeb.com

Manual