From 5ef9838ca175fa97d3ebd41cbc190a9eb1d0b8cd Mon Sep 17 00:00:00 2001 From: Matthieu Marcillaud <marcimat@rezo.net> Date: Wed, 3 Jan 2018 10:04:26 +0000 Subject: [PATCH] =?UTF-8?q?La=20page=20exec=3Dvalider=5Fxml=20n=E2=80=99es?= =?UTF-8?q?t=20pas=20directement=20utile=20au=20core=20et=20ne=20fonctionn?= =?UTF-8?q?e=20actuellement=20pas=20/=20plus.=20Elle=20est=20d=C3=A9plac?= =?UTF-8?q?=C3=A9e=20dans=20un=20plugin=20"Valider=20XML"=20si=20quelque?= =?UTF-8?q?=20personne=20est=20int=C3=A9ress=C3=A9e=20pour=20la=20reprendr?= =?UTF-8?q?e.=20https://zone.spip.org/trac/spip-zone/changeset/108307=20et?= =?UTF-8?q?=20suivant.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitattributes | 1 - ecrire/exec/valider_xml.php | 473 ------------------------------------ 2 files changed, 474 deletions(-) delete mode 100644 ecrire/exec/valider_xml.php diff --git a/.gitattributes b/.gitattributes index d7d92f3255..63075d3ef6 100644 --- a/.gitattributes +++ b/.gitattributes @@ -80,7 +80,6 @@ ecrire/exec/puce_statut.php -text ecrire/exec/rechercher.php -text ecrire/exec/selectionner.php -text ecrire/exec/upgrade.php -text -ecrire/exec/valider_xml.php -text ecrire/genie/maintenance.php -text ecrire/genie/mise_a_jour.php -text ecrire/inc/actions.php -text diff --git a/ecrire/exec/valider_xml.php b/ecrire/exec/valider_xml.php deleted file mode 100644 index a74a98bd7f..0000000000 --- a/ecrire/exec/valider_xml.php +++ /dev/null @@ -1,473 +0,0 @@ -<?php - -/***************************************************************************\ - * SPIP, Systeme de publication pour l'internet * - * * - * Copyright (c) 2001-2017 * - * Arnaud Martin, Antoine Pitrou, Philippe Riviere, Emmanuel Saint-James * - * * - * Ce programme est un logiciel libre distribue sous licence GNU/GPL. * - * Pour plus de details voir le fichier COPYING.txt ou l'aide en ligne. * -\***************************************************************************/ - -/** - * Gestion de la validation XML selon une DTD - * - * @package SPIP\Core\Valider_XML - */ - -if (!defined('_ECRIRE_INC_VERSION')) { - return; -} -include_spip('inc/presentation'); -include_spip('public/debusquer'); - - -/** - * Page d'affichage des résultats de validation XML selon une DTD - * - * - l'argument var_url peut indiquer un fichier ou un repertoire - * - l'argument ext peut valoir "php" ou "html" - * -- Si "php", le script est execute et la page valide - * -- Si "html", on suppose que c'est un squelette dont on devine les args - * en cherchant les occurrences de Pile[0]. - * - * @example - * ``` - * ecrire?exec=valider_xml&var_url=exec&ext=php pour tester l'espace prive - * ecrire?exec=valider_xml&var_url=../squelettes-dist&ext=html pour le public - * ``` - * - * @uses valider_xml_ok() - **/ -function exec_valider_xml_dist() { - if (!autoriser('webmestre')) { - include_spip('inc/minipres'); - echo minipres(); - } else { - $erreur = ""; - // verifier que les var de l'URL sont conformes avant d'appeler la fonction - $url = trim(_request('var_url')); - if (strncmp($url,'/',1)==0) $erreur = 'Chemin absolu interdit pour var_url'; - // on a pas le droit de remonter plus de 1 fois dans le path (pas 2 occurences de ../ ou ..\ (win)) - if (($p=strpos($url,'..'))!==false AND strpos($url,'..',$p+3)!==false) $erreur = 'Interdit de remonter en dehors de la racine'; - if (strpos($url,'://')!==false or strpos($url,':\\')!==false) $erreur = 'URL absolue interdite pour var_url'; - - $ext = trim(_request('ext')); - $ext = ltrim($ext,'.'); // precaution - if (preg_match('/\W/',$ext)) $erreur = 'Extension invalide'; - - // en GET var_url doit etre signee, en POST seule l'action est signee - // CSRF safe - $process = true; - if ($url){ - include_spip('inc/securiser_action'); - if ($_SERVER["REQUEST_METHOD"]=='POST'){ - if (!$token = _request('var_token') - or !verifier_cle_action("valider_xml",$token)){ - $process = false; - } - } - if ($_SERVER["REQUEST_METHOD"]!='POST'){ - if (!$token = _request('var_token') - or !verifier_cle_action("valider_xml&var_url=$url",$token)){ - $process = false; - } - } - } - - if ($erreur){ - include_spip('inc/minipres'); - echo minipres($erreur); - } - else { - valider_xml_ok($url, $ext, intval(_request('limit')), _request('recur'), $process); - } - } -} - -/** - * Vérifie le formatage d'un xml - * - * @see valider_resultats() - * @see valider_dir() - * @see valider_pseudo_url() - * - * @param string $url - * @param string $req_ext - * @param int $limit - * @param array|bool $rec - * @param bool $process - * - **/ -function valider_xml_ok($url, $req_ext, $limit, $rec, $process = true) { - $url = urldecode($url); - $rec = !$rec ? false : array(); - $res = ''; - if (!$limit) { - $limit = 200; - } - $titre = _T('analyse_xml'); - if (!$url) { - $url_aff = ''; - $bandeau = $err = ''; - } else { - include_spip('inc/distant'); - - if (is_dir($url)) { - $dir = (substr($url, -1, 1) === '/') ? $url : "$url/"; - $ext = !preg_match('/^[.*\w]+$/', $req_ext) ? 'php' : $req_ext; - $files = preg_files($dir, "$ext$", $limit, $rec); - if (!$files and $ext !== 'html') { - $files = preg_files($dir, 'html$', $limit, $rec); - if ($files) { - $ext = 'html'; - } - } - if ($files) { - $res = valider_dir($files, $ext, $url); - list($err, $res) = valider_resultats($res, $ext === 'html'); - $err = ' (' . $err . '/' . count($files) . ')'; - } else { - $res = _T('texte_vide'); - $err = ''; - } - $bandeau = $dir . '*' . $ext . $err; - } else { - if (preg_match('@^((?:[.]/)?[^?]*)[?]([0-9a-z_]+)=([^&]*)(.*)$@', $url, $r)) { - list(, $server, $dir, $script, $args) = $r; - if (((!$server) or ($server == './') - or strpos($server, url_de_base()) === 0) - and is_dir($dir) - ) { - $url = $script; - // Pour quand le validateur saura simuler - // une query-string... - // $args = preg_split('/&(amp;)?[a-z0-9_]+=/', $args); - $args = true; - } - } else { - $dir = 'exec'; - $script = $url; - $args = true; - } - - $url_aff = entites_html($url); - $bandeau = ""; - if ($process) { - $transformer_xml = charger_fonction('valider', 'xml'); - if (preg_match(',^[a-z][0-9a-z_]*$,i', $url)) { - $res = $transformer_xml(charger_fonction($url, $dir), $args); - $url_aff = valider_pseudo_url($dir, $script); - } else { - $res = $transformer_xml(recuperer_page($url)); - $url_aff = entites_html($url); - } - list($texte, $err) = emboite_texte($res); - if (!$err) { - $err = '<h3>' . _T('spip_conforme_dtd') . '</h3>'; - } - $res = - "<div style='text-align: center'>" . $err . "</div>" . - "<div style='margin: 10px; text-align: left'>" . $texte . '</div>'; - $bandeau = "<a href='$url_aff'>".$url_aff."</a>"; - } - - } - } - - $commencer_page = charger_fonction('commencer_page', 'inc'); - $debut = $commencer_page($titre); - $jq = http_script("", 'jquery.js'); - - - echo str_replace('<head>', "<head>$jq", $debut); - include_spip('inc/securiser_action'); - $token = calculer_cle_action("valider_xml"); - $texte = '<input type="text" size="70" value="' . $url_aff . '" name="var_url" id="var_url" placeholder="http://" />'; - $texte .= '<input type="hidden" value="' . $token . '" name="var_token" />'; - $texte .= '<input type="hidden" value="' . $req_ext . '" name="ext" />'; - $texte .= '<input type="submit" value="Go" />'; - $texte = generer_form_ecrire('valider_xml', $texte, " method='post'"); - - $self = generer_url_ecrire('valider_xml'); - $self = parametre_url($self, 'var_url', $url); - $self = parametre_url($self, 'ext', $req_ext); - $self = parametre_url($self, 'limit', $limit); - $self = parametre_url($self, 'rec', $rec); - $self = "<a href='$self'>$self</a>"; - - echo "<h1 class='grostitre'>", $titre, " <small>$bandeau</small>", '</h1>', - "<div style='text-align: center'>", $texte, "</div>", - $res, - "<br /><br /><p><small>$self</small></p>", - fin_page(); -} - -/** - * - * Vérifie la conformité du xml, élément par élément. - * - * @param array $res - * @param string $mode - * @return array - **/ -function valider_resultats($res, $mode) { - include_spip('inc/securiser_action'); - $i = $j = 0; - $table = ''; - rsort($res); - foreach ($res as $l) { - $i++; - $class = 'row_' . alterner($i, 'even', 'odd'); - list($nb, $texte, $erreurs, $script, $appel, $temps) = $l; - if ($texte < 0) { - $texte = (0 - $texte); - $color = ";color: red"; - } else { - $color = ''; - } - - $err = (!intval($nb)) ? '' : - ($erreurs[0][0] . ' ' . _T('ligne') . ' ' . - $erreurs[0][1] . ($nb == 1 ? '' : ' ...')); - if ($err) { - $j++; - } - if ($mode) { - $h = $appel . '&var_mode=debug&var_mode_affiche=validation'; - } - else { - $h = generer_url_ecrire('valider_xml', "var_url=" . urlencode($appel)); - $h = parametre_url($h,'var_token', calculer_cle_action("valider_xml&var_url=$appel")); - } - - $table .= "<tr class='$class'>" - . "<td style='text-align: right'>$nb</td>" - . "<td style='text-align: right$color'>$texte</td>" - . "<td style='text-align: right'>$temps</td>" - . "<td style='text-align: left'>$err</td>" - . "<td>$script</td>" - . "<td><a href='$h'>$appel</a></td>"; - } - - return array( - $j, - "<table class='spip'>" - . "<tr><th>" - . _T('erreur_texte') - . "</th><th>" - . _T('taille_octets', array('taille' => ' ')) - . "</th><th>" - . _T('zbug_profile', array('time' => '')) - . "</th><th>" - . _T('message') - . "</th><th>Page</th><th>args" - . "</th></tr>" - . $table - . "</table>" - ); -} - -/** - * Valide l'existence d'un script ou d'une fonction - * - * @uses valider_pseudo_url() - * - * @param string $transformer_xml - * @param string $script - * Nom de la fonction à charger - * @param string $dir - * Nom du répertoire qui contiendrait le fichier et/ou la fonction à chercher/charger. - * @param string $ext - * Nom de l'extension du fichier contenant la fonction à vérifier. - * @return array - */ -function valider_script($transformer_xml, $script, $dir, $ext) { - $script = basename($script, '.php'); - $dir = basename($dir); - $f = charger_fonction($script, $dir, true); - - // ne pas se controler soi-meme ni l'index du repertoire ni un fichier annexe - if ($script == _request('exec') or $script == 'index' or !$f) { - return array('/', 0, '', $script, ''); - } - - $val = $transformer_xml($f, true); - $appel = ''; - - // s'il y a l'attribut minipres, le test est non significatif - // le script necessite peut-etre des arguments, on lui en donne, - // en appelant la fonction _args associee si elle existe - // Si ca ne marche toujours pas, les arguments n'étaient pas bons - // ou c'est une authentification pour action d'administration; - // tant pis, on signale le cas par un resultat negatif - - if (strpos($val->page, "id='minipres'")) { - if (!$g = charger_fonction($script . '_args', $dir, true)) { - $res = 0 - strlen($val->page); - } else { - $args = array(1, 'id_article', 1); - $val = $transformer_xml($g, $args); - $appel = 'id_article=1&type=id_article&id=1'; - if (strpos($val->page, "id='minipres'")) { - $res = 0 - strlen($val->page); - } else { - $res = strlen($val->page); - } - } - } else { - $res = strlen($val->page); - } - - $appel = valider_pseudo_url($dir, $script, $appel); - $err = $val->err; - - return array(count($err), $res, $err, $script, $appel); -} - -/** - * Construire la bonne URL selon l'endroit où on se trouve. - * - * @param string $dir - * Par défaut, on vérifie si on est sur une page `?exec=XX` - * @param string $script - * @param string $args [description] - * @return string - */ -function valider_pseudo_url($dir, $script, $args = '') { - return ($dir == 'exec') - ? generer_url_ecrire($script, $args, false, true) - : ("./?$dir=$script" . ($args ? "&$args" : '')); -} - -/** - * Essayer de valider un texte même sans Doctype - * à moins qu'un Content-Type dise clairement que ce n'est pas du XML - * - * @param string $transformer_xml - * @param string $file - * @param string $dir - * @param string $ext - * @return array - */ -function valider_skel($transformer_xml, $file, $dir, $ext) { - if (!lire_fichier($file, $text)) { - return array('/', '/', $file, ''); - } - if (!strpos($text, 'DOCTYPE')) { - preg_match(",Content[-]Type: *\w+/(\S)+,", $text, $r); - if ($r[1] === 'css' or $r[1] === 'plain') { - return array('/', 'DOCTYPE?', $file, ''); - } - } - - if ($ext != 'html') { - // validation d'un non squelette - $page = array('texte' => $text); - $url = url_de_base() . _DIR_RESTREINT_ABS . $file; - $script = $file; - } else { - $script = basename($file, '.html'); - // pas de validation solitaire pour les squelettes internes, a revoir. - if (substr_count($dir, '/') <= 1) { - $url = generer_url_public($script, $contexte); - } else { - $url = ''; - } - $composer = charger_fonction('composer', 'public'); - list($skel_nom, $skel_code) = $composer($text, 'html', 'html', $file); - - spip_log("compilation de $file en " . strlen($skel_code) . " octets de nom $skel_nom"); - if (!$skel_nom) { - return array('/', '/', $file, ''); - } - $contexte = valider_contexte($skel_code, $file); - $page = $skel_nom(array('cache' => ''), array($contexte)); - } - $res = $transformer_xml($page['texte']); - - return array(count($res->err), strlen($res->page), $res->err, $script, $url); -} - -/** - * Analyser le code pour construire un contexte plausible complet - * - * i.e. ce qui est fourni par `$Pile[0]` - * en éliminant les exceptions venant surtout des Inclure - * - * Il faudrait trouver une typologie pour générer un contexte parfait: - * actuellement ça produit parfois des erreurs SQL à l'appel de $skel_nom - * - * @see valider_skel() - * @param string $code - * @param string $file - * @return array - */ -function valider_contexte($code, $file) { - static $exceptions = array('action', 'doublons', 'lang'); - preg_match_all('/(\S*)[$]Pile[[]0[]][[].(\w+).[]](\S*)/', $code, $r, PREG_SET_ORDER); - $args = array(); - // evacuer les repetitions et les faux parametres - foreach ($r as $v) { - list(, $f, $nom, $suite) = $v; - if (!in_array($nom, $exceptions) - and (!isset($args[$nom]) or !$args[$nom]) - ) { - $args[$nom] = ((strpos($f, 'sql_quote') !== false) - and strpos($suite, "'int'") !== false); - } - } - $contexte = array(); // etudier l'ajout de: - // 'lang' => $GLOBALS['spip_lang'], - // 'date' => date('Y-m-d H:i:s')); - foreach ($args as $nom => $f) { - if (!$f) { - $val = 'id_article'; - } else { - // on suppose que arg numerique => primary-key d'une table - // chercher laquelle et prendre un numero existant - $val = 0; - $type = (strpos($nom, 'id_') === 0) ? substr($nom, 3) : $nom; - $trouver_table = charger_fonction('trouver_table', 'base'); - $table = $trouver_table(table_objet_sql($type)); - if ($table) { - $val = @sql_getfetsel($nom, $table['table'], '', '', '', "0,1"); - } - // porte de sortie si ca marche pas, - if (!$val) { - $val = 1; - } - } - $contexte[$nom] = $val; - } - - return $contexte; -} - -/** - * Valide la conformité XML d'une liste de fichiers dans un répertoire - * - * @param array $files - * Liste des fichiers - * @param string $ext - * Extension des fichiers - * @param string $dir - * Chemin du répertoire - * @return array - **/ -function valider_dir($files, $ext, $dir) { - $res = array(); - $transformer_xml = charger_fonction('valider', 'xml'); - $valideur = $ext == 'php' ? 'valider_script' : 'valider_skel'; - foreach ($files as $f) { - spip_timer($f); - $val = $valideur($transformer_xml, $f, $dir, $ext); - $n = spip_timer($f); - $val[] = $n; - spip_log("validation de $f en $n secondes"); - $res[] = $val; - } - - return $res; -} -- GitLab