From 311b741b0f5b5c059eb3c8c232c7f5847b71d8b9 Mon Sep 17 00:00:00 2001 From: Cerdic <cedric@yterium.com> Date: Wed, 7 Sep 2022 15:15:55 +0200 Subject: [PATCH] =?UTF-8?q?feat:=20s=C3=A9parer=20la=20fonction=20qui=20sa?= =?UTF-8?q?nitize=20le=20source=20du=20SVG=20pour=20pouvoir=20l'utiliser?= =?UTF-8?q?=20dans=20un=20autre=20contexte?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Refs: https://git.spip.net/spip/safehtml/issues/4786 --- sanitizer/svg.php | 103 ++++++++++++++++++++++++++++------------------ 1 file changed, 62 insertions(+), 41 deletions(-) diff --git a/sanitizer/svg.php b/sanitizer/svg.php index 13d842a2..d57431b2 100644 --- a/sanitizer/svg.php +++ b/sanitizer/svg.php @@ -29,13 +29,21 @@ include_spip('inc/autoriser'); * cf http://www.slideshare.net/x00mario/the-image-that-called-me * http://heideri.ch/svgpurifier/SVGPurifier/index.php * - * @param string $file - * @return array Tableau (largeur, hauteur) + * @param string $file_or_svg + * @return bool */ -function sanitizer_svg_dist($file) { +function sanitizer_svg_dist($file_or_svg) { include_spip('inc/svg'); - if ($svg = svg_charger($file)) { + if ($svg = svg_charger($file_or_svg)) { + if ($svg === $file_or_svg) { + $file = false; + } + else { + $file = $file_or_svg; + } + unset($file_or_svg); + // forcer une viewBox et width+height en px $svg = svg_force_viewBox_px($svg, true); @@ -46,43 +54,7 @@ function sanitizer_svg_dist($file) { // qu'on soit admin ou non, on sanitize les SVGs car rien ne dit qu'un admin sait que ca contient du JS // and !autoriser('televerser', 'script') ) { - spip_log("sanitization SVG $file", 'svg'); - - if (!class_exists('enshrined\svgSanitize\Sanitizer')) { - spl_autoload_register(function ($class) { - $prefix = 'enshrined\\svgSanitize\\'; - $base_dir = _DIR_PLUGIN_MEDIAS . 'lib/svg-sanitizer/src/'; - $len = strlen($prefix); - if (strncmp($prefix, $class, $len) !== 0) { - return; - } - $relative_class = substr($class, $len); - $file = $base_dir . str_replace('\\', '/', $relative_class) . '.php'; - if (file_exists($file)) { - require $file; - } - }); - } - - // sanitization can need multiples call - $maxiter = 10; - do { - $size = strlen($svg); - $sanitizer = new Sanitizer(); - $sanitizer->setXMLOptions(0); // garder les balises vide en ecriture raccourcie - - // Pass it to the sanitizer and get it back clean - $svg = $sanitizer->sanitize($svg); - - // loger les sanitization - $trace = ''; - foreach ($sanitizer->getXmlIssues() as $issue) { - $trace .= $issue['message'] . ' L' . $issue['line'] . "\n"; - } - if ($trace) { - spip_log($trace, 'svg' . _LOG_DEBUG); - } - } while (strlen($svg) !== $size and $maxiter-- > 0); + $svg = sanitizer_svg_string($svg, $file); } ecrire_fichier($file, $svg); @@ -93,3 +65,52 @@ function sanitizer_svg_dist($file) { // pas de svg valide return false; } + +/** + * @param string $svg + * @param string $fileName + * @return false|string + */ +function sanitizer_svg_string($svg, $fileName = '') { + + $tracesvg = ($fileName ?: substr($svg, 0,32)."...(".strlen($svg). "c ". md5($svg) . ")"); + spip_log("sanitization SVG $tracesvg", 'svg' . _LOG_DEBUG); + + if (!class_exists('enshrined\svgSanitize\Sanitizer')) { + spl_autoload_register(function ($class) { + $prefix = 'enshrined\\svgSanitize\\'; + $base_dir = _DIR_PLUGIN_MEDIAS . 'lib/svg-sanitizer/src/'; + $len = strlen($prefix); + if (strncmp($prefix, $class, $len) !== 0) { + return; + } + $relative_class = substr($class, $len); + $file = $base_dir . str_replace('\\', '/', $relative_class) . '.php'; + if (file_exists($file)) { + require $file; + } + }); + } + + // sanitization can need multiples call + $maxiter = 10; + do { + $size = strlen($svg); + $sanitizer = new Sanitizer(); + $sanitizer->setXMLOptions(0); // garder les balises vide en ecriture raccourcie + + // Pass it to the sanitizer and get it back clean + $svg = $sanitizer->sanitize($svg); + + // loger les sanitization + $trace = ''; + foreach ($sanitizer->getXmlIssues() as $issue) { + $trace .= $issue['message'] . ' L' . $issue['line'] . "\n"; + } + if ($trace) { + spip_log($trace, 'svg' . _LOG_DEBUG); + } + } while (strlen($svg) !== $size and $maxiter-- > 0); + + return $svg; +} -- GitLab