From 7e8fe71d26fcfc414b365514ea00b002efddb698 Mon Sep 17 00:00:00 2001 From: "Committo,Ergo:sum" <esj@rezo.net> Date: Wed, 20 Dec 2006 19:47:48 +0000 Subject: [PATCH] =?UTF-8?q?Simplification=20de=20l'interface=20=C3=A0=20l'?= =?UTF-8?q?indenteur/validateur,=20d'une=20part=20pour=20que=20l'indenteur?= =?UTF-8?q?=20ne=20s'encombre=20pas=20des=20donn=C3=A9es=20du=20validateur?= =?UTF-8?q?,=20et=20pour=20qu'on=20puisse=20=C3=A9crire=20des=20validateur?= =?UTF-8?q?=20meilleurs=20que=20celui=20du=20W3C=20en=20r=C3=A9cup=C3=A9ra?= =?UTF-8?q?nt=20un=20maximum=20de=20code.=20Il=20y=20a=20peu=20de=20progra?= =?UTF-8?q?mmation=20objet,=20mais=20entre=20les=20incompatibilit=C3=A9s?= =?UTF-8?q?=20de=20PHP4=20et=20PHP5=20sur=20la=20question,=20et=20la=20fol?= =?UTF-8?q?ie=20de=20la=20s=C3=A9mantique=20de=20r=C3=A9f=C3=A9rence=20dan?= =?UTF-8?q?s=20les=20deux=20cas,=20c'est=20minimal.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit A présent, il faut affecter dans mes_options.php une seule variable, qui sera le nom passé à charger_fonction à la fin de ecrire/index.php: {{{ $GLOBALS['transformer_xml'] = 'indenter_xml'; // pour l'indenteur XML $GLOBALS['transformer_xml'] = 'valider_xml'; // pour le validateur par DTD }}} Les spécifications de [8136] n'auront donc vécu que le temps de 13 dépots. --- .gitattributes | 3 +- ecrire/inc/formater_article.php | 2 +- ecrire/inc/indenter_xml.php | 56 ++++ ecrire/inc/instituer_auteur.php | 2 +- ecrire/inc/sax.php | 283 ++++++++---------- .../inc/{validateur.php => valider_xml.php} | 85 +++++- ecrire/index.php | 7 +- ecrire/public/debug.php | 4 +- 8 files changed, 263 insertions(+), 179 deletions(-) create mode 100644 ecrire/inc/indenter_xml.php rename ecrire/inc/{validateur.php => valider_xml.php} (80%) diff --git a/.gitattributes b/.gitattributes index a483daae8f..ee0d0b81c7 100644 --- a/.gitattributes +++ b/.gitattributes @@ -486,6 +486,7 @@ ecrire/inc/import_0_0.php -text ecrire/inc/import_1_2.php -text ecrire/inc/import_1_3.php -text ecrire/inc/import_insere.php -text +ecrire/inc/indenter_xml.php -text ecrire/inc/informer.php -text ecrire/inc/informer_auteur.php -text ecrire/inc/instituer_article.php -text @@ -515,7 +516,7 @@ ecrire/inc/syndic.php -text ecrire/inc/tourner.php -text ecrire/inc/traduire.php -text ecrire/inc/utils.php -text -ecrire/inc/validateur.php -text +ecrire/inc/valider_xml.php -text ecrire/inc/vieilles_defs.php -text ecrire/inc/virtualiser.php -text ecrire/inc/xml.php -text diff --git a/ecrire/inc/formater_article.php b/ecrire/inc/formater_article.php index bc153e95b7..c740433486 100644 --- a/ecrire/inc/formater_article.php +++ b/ecrire/inc/formater_article.php @@ -66,7 +66,7 @@ function inc_formater_article_dist($row) . $dir_lang . " style=\"display:block;\">" . (!$logo ? '' : - ("<div style='float: $spip_lang_right; margin-top: -2px; margin-bottom: -2px;'>" . $logo . "</div>")) + ("<span style='float: $spip_lang_right; margin-top: -2px; margin-bottom: -2px;'>" . $logo . "</span>")) . (acces_restreint_rubrique($id_rubrique) ? $img_admin : '') . typo($titre) . (!($afficher_langue AND $lang != $GLOBALS['meta']['langue_site']) ? '' : diff --git a/ecrire/inc/indenter_xml.php b/ecrire/inc/indenter_xml.php new file mode 100644 index 0000000000..b09e274754 --- /dev/null +++ b/ecrire/inc/indenter_xml.php @@ -0,0 +1,56 @@ +<?php + +/***************************************************************************\ + * SPIP, Systeme de publication pour l'internet * + * * + * Copyright (c) 2001-2007 * + * 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. * +\***************************************************************************/ + +if (!defined("_ECRIRE_INC_VERSION")) return; + +include_spip('inc/sax'); + +class IndenteurXML { + +function debutElement($phraseur, $name, $attrs) +{ xml_debutElement($phraseur, $name, $attrs);} + +function finElement($phraseur, $name) +{ xml_finElement($phraseur, $name);} + +function textElement($phraseur, $data) +{ xml_textElement($phraseur, $data);} + +function PiElement($phraseur, $target, $data) +{ xml_PiElement($phraseur, $target, $data);} + +function defautElement($phraseur, $data) +{ xml_defautElement($phraseur, $data);} + +function phraserTout($phraseur, $data) +{ + xml_parsestring($phraseur, $data); + return !$this->err ? $this->res : join('<br />', $this->err) . '<br />'; +} + + var $depth = ""; + var $res = ""; + var $err = array(); + var $contenu = array(); + var $ouvrant = array(); + var $reperes = array(); + var $entites = array(); +} + +function inc_indenter_xml_dist($page, $apply=false) +{ + $sax = charger_fonction('sax', 'inc'); + return $sax($page, $apply, $GLOBALS['phraseur_xml'] = new IndenteurXML()); + +} + +?> diff --git a/ecrire/inc/instituer_auteur.php b/ecrire/inc/instituer_auteur.php index e1f0715f09..1b05e83546 100644 --- a/ecrire/inc/instituer_auteur.php +++ b/ecrire/inc/instituer_auteur.php @@ -131,7 +131,7 @@ function choix_statut_auteur($statut, $ancre) { global $connect_toutes_rubriques; $menu = "<select name='statut' size='1' class='fondl' - onChange=\"findObj_forcer('$ancre').style.visibility = (this.selectedIndex ? 'hidden' : 'visible');\">"; + onchange=\"findObj_forcer('$ancre').style.visibility = (this.selectedIndex ? 'hidden' : 'visible');\">"; // Si on est admin restreint, on n'a pas le droit de modifier un admin if ($connect_toutes_rubriques) diff --git a/ecrire/inc/sax.php b/ecrire/inc/sax.php index e5f8ee2ba2..f68a1b6484 100644 --- a/ecrire/inc/sax.php +++ b/ecrire/inc/sax.php @@ -15,147 +15,121 @@ if (!defined("_ECRIRE_INC_VERSION")) return; include_spip('inc/filtres'); include_spip('inc/charsets'); -// http://doc.spip.org/@PhraseurXML -class PhraseurXML { - // http://doc.spip.org/@debutElement -function debutElement($parser, $name, $attrs) +function xml_debutElement($parser, $name, $attrs) { - global $phraseur_xml; - - if ($phraseur_xml->elements) - validerElement($parser, $name, $attrs); - - $depth = &$phraseur_xml->depth; - $contenu = &$phraseur_xml->contenu; - $ouvrant = &$phraseur_xml->ouvrant; - $reperes = &$phraseur_xml->reperes; - $res = &$phraseur_xml->res; - - $t = isset($ouvrant[$depth]) ? $ouvrant[$depth] : ' '; - // espace initial signifie: deja integree au resultat - if ($t[0] != ' ') - { - $res .= '<' . $t . '>'; - $ouvrant[$depth] = ' ' . $t; - } - $t = $contenu[$depth]; - // n'indenter que s'il y a un separateur avant - $res .= ereg_replace("[\n\t ]+$", "\n$depth", $t); - $contenu[$depth] = ""; - $att = ''; - $sep = ' '; - foreach ($attrs as $k => $v) { - if ($phraseur_xml->attributs) - validerAttribut($parser, $k, $v, $name); - $delim = strpos($v, "'") === false ? "'" : '"'; - $val = entites_html($v); - $att .= $sep . $k . "=" . $delim - . ($delim !== '"' ? str_replace('"', '"', $val) : $val) - . $delim; - $sep = "\n $depth"; - } - $depth .= ' '; - $contenu[$depth] = ""; - $ouvrant[$depth] = $name . $att; - $reperes[$depth] = xml_get_current_line_number($parser); + global $phraseur_xml; + $depth = &$phraseur_xml->depth; + $contenu = &$phraseur_xml->contenu; + $ouvrant = &$phraseur_xml->ouvrant; + $reperes = &$phraseur_xml->reperes; + + $t = isset($ouvrant[$depth]) ? $ouvrant[$depth] : ' '; + // espace initial signifie: deja integree au resultat + if ($t[0] != ' ') + { + $phraseur_xml->res .= '<' . $t . '>'; + $ouvrant[$depth] = ' ' . $t; + } + $t = $contenu[$depth]; + // n'indenter que s'il y a un separateur avant + $phraseur_xml->res .= ereg_replace("[\n\t ]+$", "\n$depth", $t); + $contenu[$depth] = ""; + $att = ''; + $sep = ' '; + foreach ($attrs as $k => $v) { + $delim = strpos($v, "'") === false ? "'" : '"'; + $val = entites_html($v); + $att .= $sep . $k . "=" . $delim + . ($delim !== '"' ? str_replace('"', '"', $val) : $val) + . $delim; + $sep = "\n $depth"; + } + $depth .= ' '; + $contenu[$depth] = ""; + $ouvrant[$depth] = $name . $att; + $reperes[$depth] = xml_get_current_line_number($parser); } // http://doc.spip.org/@finElement -function finElement($parser, $name) +function xml_finElement($parser, $name, $fusion_bal=false) { - global $phraseur_xml; - $depth = &$phraseur_xml->depth; - $contenu = &$phraseur_xml->contenu; - $ouvrant = &$phraseur_xml->ouvrant; - $res = &$phraseur_xml->res; - - $ouv = $ouvrant[$depth]; - if ($ouv[0] != ' ') - $ouvrant[$depth] = ' ' . $ouv; - else $ouv= ""; - $t = $contenu[$depth]; - $depth = substr($depth, 2); - $t = ereg_replace("[\n\t ]+$", "\n" . $depth, $t); + global $phraseur_xml; + $depth = &$phraseur_xml->depth; + $contenu = &$phraseur_xml->contenu; + $ouvrant = &$phraseur_xml->ouvrant; + + $ouv = $ouvrant[$depth]; + if ($ouv[0] != ' ') + $ouvrant[$depth] = ' ' . $ouv; + else $ouv= ""; + $t = $contenu[$depth]; + $depth = substr($depth, 2); + $t = ereg_replace("[\n\t ]+$", "\n" . $depth, $t); + // fusion <balise></balise> en <balise />. - // ATTENTION, en presence d'attributs ne le faire que si la DTD le dit: - // pour les autres, certains clients http croient que fusion ==> pas d'att + // ATTENTION, certains clients http croient que fusion ==> pas d'atttributs // en particulier pour les balises Script et A. - if ($t || (($ouv !=$name) AND $phraseur_xml->elements[$name][0] != 'EMPTY')) - $res .= ($ouv ? ('<' . $ouv . '>') : '') . $t . "</" . $name . ">"; - else - $res .= ($ouv ? ('<' . $ouv . ' />') : ("</" . $name . ">")); + // en presence d'attributs ne le faire que si la DTD est dispo et d'accord + // (param fusion_bal) + + if ($t || (($ouv != $name) AND !$fusion_bal)) + $phraseur_xml->res .= ($ouv ? ('<' . $ouv . '>') : '') . $t . "</" . $name . ">"; + else + $phraseur_xml->res .= ($ouv ? ('<' . $ouv . ' />') : ("</" . $name . ">")); } // http://doc.spip.org/@textElement -function textElement($parser, $data) +function xml_textElement($parser, $data) { - global $phraseur_xml; - $depth = &$phraseur_xml->depth; - $contenu = &$phraseur_xml->contenu; - $contenu[$depth] .= preg_match('/^script/',$phraseur_xml->ouvrant[$depth]) - ? $data - : entites_html($data); + global $phraseur_xml; + + $depth = &$phraseur_xml->depth; + $contenu = &$phraseur_xml->contenu; + $contenu[$depth] .= preg_match('/^script/',$phraseur_xml->ouvrant[$depth]) + ? $data + : entites_html($data); } // http://doc.spip.org/@PiElement -function PiElement($parser, $target, $data) +function xml_PiElement($parser, $target, $data) { - global $phraseur_xml, $xml_parser; - $depth = &$phraseur_xml->depth; - $contenu = &$phraseur_xml->contenu; - if (strtolower($target) != "php") - $contenu[$depth] .= $data; - else { - ob_start(); - eval($data); - $data = ob_get_contents(); - ob_end_clean(); + global $phraseur_xml; + $depth = &$phraseur_xml->depth; + $contenu = &$phraseur_xml->contenu; + if (strtolower($target) != "php") $contenu[$depth] .= $data; - } + else { + ob_start(); + eval($data); + $data = ob_get_contents(); + ob_end_clean(); + $contenu[$depth] .= $data; + } } // http://doc.spip.org/@defautElement -function defautElement($parser, $data) +function xml_defautElement($parser, $data) { - global $phraseur_xml; - $depth = &$phraseur_xml->depth; - $contenu = &$phraseur_xml->contenu; - - if (!isset($contenu[$depth])) $contenu[$depth]=''; - $contenu[$depth] .= $data; -} + global $phraseur_xml; + $depth = &$phraseur_xml->depth; + $contenu = &$phraseur_xml->contenu; -// http://doc.spip.org/@xml_parsefile -function xml_parsefile($phraseur, $file) -{ - if (!($fp = fopen($file, "r"))) { - include_spip('inc/minipres'); - echo minipres("Impossible d'ouvrir le fichier XML"); - exit; - } - while ($data = fread($fp, 4096)) { - if (!xml_parse($phraseur, - str_replace('’',"'",$data), feof($fp))) { - return (sprintf("erreur XML : %s ligne %d", - xml_error_string(xml_get_error_code($phraseur)), - xml_get_current_line_number($phraseur))); - } - } - return ""; + if (!isset($contenu[$depth])) $contenu[$depth]=''; + $contenu[$depth] .= $data; } // http://doc.spip.org/@xml_parsestring function xml_parsestring($phraseur, $data) { global $phraseur_xml; - $phraseur_xml->contenu[$phraseur_xml->depth] =''; if (!xml_parse($phraseur, $data, true)) { // ne pas commencer le message par un "<" (cf inc_sax_dist) - return xml_error_string(xml_get_error_code($phraseur)) . + $phraseur_xml->err = array( + xml_error_string(xml_get_error_code($phraseur)) . coordonnees_erreur($phraseur) . '<br />' . (!$phraseur_xml->depth ? '' : ( @@ -165,49 +139,47 @@ function xml_parsestring($phraseur, $data) "</tt>" . _L(" ligne ") . $phraseur_xml->reperes[$phraseur_xml->depth] . - '<br />' )); - } - foreach ($phraseur_xml->idrefs as $idref) { - list($nom, $ligne, $col) = $idref; - if (!isset($phraseur_xml->ids[$nom])) - $phraseur_xml->err[]= " <p><b>$nom</b>" - . _L(" ID inconnu ") - . $ligne - . " " - . $col; + '<br />' ))); } - if ($phraseur_xml->err) - return join('<br />', $phraseur_xml->err) . '<br />'; - - return $phraseur_xml->res; } - var $depth = ""; - var $res = ""; - var $contenu = array(); - var $ouvrant = array(); - var $reperes = array(); - var $elements = array(); - var $peres = array(); - var $entites = array(); - var $attributs = array(); - var $ids = array(); - var $idrefs = array(); - var $err = array(); +// http://doc.spip.org/@coordonnees_erreur +function coordonnees_erreur($xml_parser) +{ + return + ' ' . + xml_get_current_line_number($xml_parser) . + ' ' . + xml_get_current_column_number($xml_parser); } -// http://doc.spip.org/@inc_sax_dist -function inc_sax_dist($page, $apply=false) { - global $phraseur_xml, $xml_parser; +function inc_sax_dist($page, $apply=false) +{ + global $phraseur_xml; + + // init par defaut si pas fait (espace public) + if (!isset($GLOBALS['phraseur_xml'])) { + $indenter_xml = charger_fonction('indenter_xml', 'inc'); + return $indenter_xml($page, $apply); + } $xml_parser = xml_parser_create($GLOBALS['meta']['charset']); + xml_set_element_handler($xml_parser, array($phraseur_xml, "debutElement"), array($phraseur_xml, "finElement")); - xml_set_character_data_handler($xml_parser, array($phraseur_xml, "textElement")); - xml_set_processing_instruction_handler($xml_parser, array($phraseur_xml, 'PiElement')); - xml_set_default_handler($xml_parser, array($phraseur_xml, "defautElement")); + + xml_set_character_data_handler($xml_parser, + array($phraseur_xml, "textElement")); + + xml_set_processing_instruction_handler($xml_parser, + array($phraseur_xml, 'PiElement')); + + xml_set_default_handler($xml_parser, + array($phraseur_xml, "defautElement")); + xml_parser_set_option($xml_parser, XML_OPTION_CASE_FOLDING, false); + unset($GLOBALS['xhtml_error']); if ($apply) { @@ -216,34 +188,15 @@ function inc_sax_dist($page, $apply=false) { $page = ob_get_contents(); ob_end_clean(); } - if ($GLOBALS['xml_validation'] - AND $validateur = charger_fonction('validateur', 'inc', true)) { - $validateur($page); - if (isset($phraseur_xml->entites['HTMLsymbol'])) - $page = unicode2charset(html2unicode($page, true)); - } - $res = $phraseur_xml->xml_parsestring($xml_parser, $page); + + $res = $phraseur_xml->phraserTout($xml_parser, $page); + xml_parser_free($xml_parser); - if ($res[0] != '<') - $GLOBALS['xhtml_error'] = $res; - else - $page = $res; - return $page; -} + if ($res[0] == '<') return $res; -// http://doc.spip.org/@coordonnees_erreur -function coordonnees_erreur($xml_parser) -{ - return - ' ' . - xml_get_current_line_number($xml_parser) . - ' ' . - xml_get_current_column_number($xml_parser); + $GLOBALS['xhtml_error'] = $res; + return $page; } -$GLOBALS['phraseur_xml'] = new PhraseurXML(); -// exemple d'appel en ligne de commande: -#$error = $phraseur_xml->xml_parsefile($xml_parser, $_SERVER['argv'][1]); - ?> diff --git a/ecrire/inc/validateur.php b/ecrire/inc/valider_xml.php similarity index 80% rename from ecrire/inc/validateur.php rename to ecrire/inc/valider_xml.php index e892019fd6..858bd443de 100644 --- a/ecrire/inc/validateur.php +++ b/ecrire/inc/valider_xml.php @@ -10,21 +10,20 @@ * Pour plus de details voir le fichier COPYING.txt ou l'aide en ligne. * \***************************************************************************/ - if (!defined("_ECRIRE_INC_VERSION")) return; +include_spip('inc/sax'); + define('_REGEXP_DOCTYPE', '/^\s*(<[?][^>]*>\s*)?<!DOCTYPE\s+(\w+)\s+(\w+)\s*([^>]*)>/'); - -// http://doc.spip.org/@inc_validateur_dist -function inc_validateur_dist($data) +function validateur($data) { global $phraseur_xml; - if (!preg_match(_REGEXP_DOCTYPE, $data, $r)) return array(); + list(,,$topelement, $avail,$suite) = $r; if (!preg_match('/^"([^"]*)"\s*(.*)$/', $suite, $r)) @@ -93,7 +92,7 @@ function inc_validateur_dist($data) asort($v); $phraseur_xml->peres[$k] = $v; } - } + } $phraseur_xml->elements = $res; $res = array(); @@ -223,4 +222,78 @@ function validerAttribut($parser, $name, $val, $bal) } } } + +class ValidateurXML { + +function debutElement($phraseur, $name, $attrs) +{ + + validerElement($phraseur, $name, $attrs); + xml_debutElement($phraseur, $name, $attrs); + foreach ($attrs as $k => $v) { + validerAttribut($phraseur, $k, $v, $name); + } +} + +function finElement($phraseur, $name) +{ + global $phraseur_xml; + xml_finElement($phraseur, + $name, + $phraseur_xml->elements[$name][0] == 'EMPTY'); +} + +function textElement($phraseur, $data) +{ xml_textElement($phraseur, $data);} + +function PiElement($phraseur, $target, $data) +{ xml_PiElement($phraseur, $target, $data);} + +function defautElement($phraseur, $data) +{ xml_defautElement($phraseur, $data);} + +function phraserTout($phraseur, $data) +{ + validateur($data); + if (isset($this->entites['HTMLsymbol'])) + $data = unicode2charset(html2unicode($data, true)); + + + xml_parsestring($phraseur, $data); + + if (!$phraseur_xml->err) { + foreach ($this->idrefs as $idref) { + list($nom, $ligne, $col) = $idref; + if (!isset($phraseur_xml->ids[$nom])) + $this->err[]= " <p><b>$nom</b>" + . _L(" ID inconnu ") + . $ligne + . " " + . $col; + } + } + + return !$this->err ? $this->res : join('<br />', $this->err) . '<br />'; +} + + var $depth = ""; + var $res = ""; + var $contenu = array(); + var $ouvrant = array(); + var $reperes = array(); + var $elements = array(); + var $peres = array(); + var $entites = array(); + var $attributs = array(); + var $ids = array(); + var $idrefs = array(); + var $err = array(); +} + +function inc_valider_xml_dist($page, $apply=false) +{ + $sax = charger_fonction('sax', 'inc'); + return $sax($page, $apply, $GLOBALS['phraseur_xml'] = new ValidateurXML()); + +} ?> diff --git a/ecrire/index.php b/ecrire/index.php index 7ec915941d..25ae5ed6d8 100644 --- a/ecrire/index.php +++ b/ecrire/index.php @@ -201,8 +201,11 @@ AND $l = @unserialize($l)) { // Trouver la fonction eventuellement surchagee et l'appeler. $var_f = charger_fonction($exec); -if (!$GLOBALS['xml_indent'] +if (!$GLOBALS['transformer_xml'] OR $GLOBALS['auteur_session']['statut']!='0minirezo') $var_f(); - else { include('public/debug.php'); debug_script($var_f); } + else { include('public/debug.php'); + $transformer_xml=charger_fonction($GLOBALS['transformer_xml'], 'inc'); + debug_script($transformer_xml($var_f, true)); + } ?> diff --git a/ecrire/public/debug.php b/ecrire/public/debug.php index 70af58fd5d..9b82aec1a3 100644 --- a/ecrire/public/debug.php +++ b/ecrire/public/debug.php @@ -474,10 +474,8 @@ function debug_dumpfile ($texte, $fonc, $type) { // Fonction pour l'espace de redaction, appeler par ecrire/index.php // http://doc.spip.org/@debug_script -function debug_script ($fonc) { +function debug_script ($t) { - $sax = charger_fonction($GLOBALS['xml_indent'], 'inc'); - $t = $sax($fonc, true); if (!isset($GLOBALS['xhtml_error'])) echo $t; else { -- GitLab