| [ Index ] |
|
Code source de SPIP 1.9.2c |
1 <?php 2 3 /***************************************************************************\ 4 * SPIP, Systeme de publication pour l'internet * 5 * * 6 * Copyright (c) 2001-2007 * 7 * Arnaud Martin, Antoine Pitrou, Philippe Riviere, Emmanuel Saint-James * 8 * * 9 * Ce programme est un logiciel libre distribue sous licence GNU/GPL. * 10 * Pour plus de details voir le fichier COPYING.txt ou l'aide en ligne. * 11 \***************************************************************************/ 12 13 if (!defined("_ECRIRE_INC_VERSION")) return; 14 15 include_spip('inc/filtres'); 16 include_spip('inc/charsets'); 17 include_spip('xml/interfaces'); 18 19 // http://doc.spip.org/@xml_debutElement 20 function xml_debutElement($parser, $name, $attrs) 21 { 22 global $phraseur_xml; 23 $depth = &$phraseur_xml->depth; 24 $contenu = &$phraseur_xml->contenu; 25 $ouvrant = &$phraseur_xml->ouvrant; 26 $reperes = &$phraseur_xml->reperes; 27 28 $t = isset($ouvrant[$depth]) ? $ouvrant[$depth] : ' '; 29 // espace initial signifie: deja integree au resultat 30 if ($t[0] != ' ') 31 { 32 $phraseur_xml->res .= '<' . $t . '>'; 33 $ouvrant[$depth] = ' ' . $t; 34 } 35 $t = $contenu[$depth]; 36 // n'indenter que s'il y a un separateur avant 37 $phraseur_xml->res .= ereg_replace("[\n\t ]+$", "\n$depth", $t); 38 $contenu[$depth] = ""; 39 $att = ''; 40 $sep = ' '; 41 foreach ($attrs as $k => $v) { 42 $delim = strpos($v, "'") === false ? "'" : '"'; 43 $val = entites_html($v); 44 $att .= $sep . $k . "=" . $delim 45 . ($delim !== '"' ? str_replace('"', '"', $val) : $val) 46 . $delim; 47 $sep = "\n $depth"; 48 } 49 $depth .= ' '; 50 $contenu[$depth] = ""; 51 $ouvrant[$depth] = $name . $att; 52 $reperes[$depth] = xml_get_current_line_number($parser); 53 } 54 55 // http://doc.spip.org/@xml_finElement 56 function xml_finElement($parser, $name, $fusion_bal=false) 57 { 58 global $phraseur_xml; 59 $depth = &$phraseur_xml->depth; 60 $contenu = &$phraseur_xml->contenu; 61 $ouvrant = &$phraseur_xml->ouvrant; 62 63 $ouv = $ouvrant[$depth]; 64 65 if ($ouv[0] != ' ') 66 $ouvrant[$depth] = ' ' . $ouv; 67 else $ouv= ""; 68 $t = $contenu[$depth]; 69 $depth = substr($depth, 2); 70 $t = ereg_replace("[\n\t ]+$", "\n" . $depth, $t); 71 72 // fusion <balise></balise> en <balise />. 73 // ATTENTION, certains clients http croient que fusion ==> pas d'atttributs 74 // en particulier pour les balises Script et A. 75 // en presence d'attributs ne le faire que si la DTD est dispo et d'accord 76 // (param fusion_bal) 77 78 if ($t || (($ouv != $name) AND !$fusion_bal)) 79 $phraseur_xml->res .= ($ouv ? ('<' . $ouv . '>') : '') . $t . "</" . $name . ">"; 80 else 81 $phraseur_xml->res .= ($ouv ? ('<' . $ouv . ' />') : ("</" . $name . ">")); 82 } 83 84 // http://doc.spip.org/@xml_textElement 85 function xml_textElement($parser, $data) 86 { 87 global $phraseur_xml; 88 89 $depth = &$phraseur_xml->depth; 90 $contenu = &$phraseur_xml->contenu; 91 $contenu[$depth] .= preg_match('/^script/',$phraseur_xml->ouvrant[$depth]) 92 ? $data 93 : entites_html($data); 94 } 95 96 // http://doc.spip.org/@xml_PiElement 97 function xml_PiElement($parser, $target, $data) 98 { 99 global $phraseur_xml; 100 $depth = &$phraseur_xml->depth; 101 $contenu = &$phraseur_xml->contenu; 102 if (strtolower($target) != "php") 103 $contenu[$depth] .= $data; 104 else { 105 ob_start(); 106 eval($data); 107 $data = ob_get_contents(); 108 ob_end_clean(); 109 $contenu[$depth] .= $data; 110 } 111 } 112 113 114 // http://doc.spip.org/@xml_defautElement 115 function xml_defautElement($parser, $data) 116 { 117 global $phraseur_xml; 118 $depth = &$phraseur_xml->depth; 119 $contenu = &$phraseur_xml->contenu; 120 121 if (!isset($contenu[$depth])) $contenu[$depth]=''; 122 $contenu[$depth] .= $data; 123 } 124 125 // http://doc.spip.org/@xml_parsestring 126 function xml_parsestring($phraseur, $data) 127 { 128 global $phraseur_xml; 129 $phraseur_xml->contenu[$phraseur_xml->depth] =''; 130 131 if (!xml_parse($phraseur, $data, true)) { 132 // ne pas commencer le message par un "<" (cf inc_sax_dist) 133 $phraseur_xml->err = array( 134 xml_error_string(xml_get_error_code($phraseur)) . 135 coordonnees_erreur($phraseur) . "<br />\n" . 136 (!$phraseur_xml->depth ? '' : 137 ( 138 _T('erreur_balise_non_fermee') . 139 " <tt>" . 140 $phraseur_xml->ouvrant[$phraseur_xml->depth] . 141 "</tt> " . 142 _T('ligne') . 143 $phraseur_xml->reperes[$phraseur_xml->depth] . 144 " <br />\n" ))); 145 } 146 } 147 148 // http://doc.spip.org/@coordonnees_erreur 149 function coordonnees_erreur($xml_parser) 150 { 151 return 152 ' ' . 153 xml_get_current_line_number($xml_parser) . 154 ' ' . 155 xml_get_current_column_number($xml_parser); 156 } 157 158 // http://doc.spip.org/@inc_sax_dist 159 function inc_sax_dist($page, $apply=false) 160 { 161 global $phraseur_xml; 162 163 // init par defaut si pas fait (espace public) 164 if (!isset($GLOBALS['phraseur_xml'])) { 165 $indenter_xml = charger_fonction('indenter_xml', 'inc'); 166 return $indenter_xml($page, $apply); 167 } 168 169 $xml_parser = xml_parser_create($GLOBALS['meta']['charset']); 170 171 xml_set_element_handler($xml_parser, 172 array($phraseur_xml, "debutElement"), 173 array($phraseur_xml, "finElement")); 174 175 xml_set_character_data_handler($xml_parser, 176 array($phraseur_xml, "textElement")); 177 178 xml_set_processing_instruction_handler($xml_parser, 179 array($phraseur_xml, 'PiElement')); 180 181 xml_set_default_handler($xml_parser, 182 array($phraseur_xml, "defautElement")); 183 184 xml_parser_set_option($xml_parser, XML_OPTION_CASE_FOLDING, false); 185 186 unset($GLOBALS['xhtml_error']); 187 188 if ($apply) { 189 ob_start(); 190 $page(); 191 $page = ob_get_contents(); 192 ob_end_clean(); 193 } 194 195 // charger la DTD et transcoder les entites, 196 // et escamoter le doctype que sax mange en php 5 197 list($doctype,$page) = sax_bug($page); 198 199 $res = $phraseur_xml->phraserTout($xml_parser, $page); 200 201 xml_parser_free($xml_parser); 202 203 if ($res[0] == '<'){ 204 if (!preg_match(_REGEXP_DOCTYPE, substr($res,0,strlen($doctype)))) 205 $res = $doctype . $res; 206 return $res; 207 } 208 209 $GLOBALS['xhtml_error'] = $res; 210 211 return $page; 212 } 213 214 // SAX ne dit pas si une Entite est dans un attribut ou non. 215 // Les eliminer toutes sinon celles des attributs apparaissent en zone texte! 216 // Celles fondamentales pour la lecture (lt gt quot amp) sont conservees 217 // (d'ailleurs SAX ne les considere pas comme des entites dans un attribut) 218 // Si la DTD est dispo, on va chercher les entites dedans 219 // sinon on se rabat sur ce qu'en connait SPIP en standard. 220 221 // http://doc.spip.org/@sax_bug 222 function sax_bug($data) 223 { 224 global $phraseur_xml; 225 $doctype = ""; 226 227 $r = analyser_doctype($data); 228 if (!$r) { 229 $data = _MESSAGE_DOCTYPE . _DOCTYPE_ECRIRE 230 . preg_replace(_REGEXP_DOCTYPE, '', $data); 231 $r = analyser_doctype($data); 232 } 233 234 list($doctype, $topelement, $avail, $grammaire, $rotlvl) = $r; 235 236 //$data = str_replace('DOCTYPE','doctype',$doctype).substr($data,strlen($doctype)); 237 $file = _DIR_CACHE_XML . preg_replace('/[^\w.]/','_', $rotlvl) . '.gz'; 238 239 if (lire_fichier($file, $r)) { 240 $phraseur_xml->dtc = unserialize($r); 241 } else { 242 include_spip('xml/analyser_dtd'); 243 $phraseur_xml->dtc = charger_dtd($grammaire, $avail); 244 if (($avail == 'PUBLIC' ) AND $phraseur_xml->dtc) 245 ecrire_fichier($file, serialize($phraseur_xml->dtc), true); 246 } 247 248 if ($phraseur_xml->dtc) { 249 $trans = array(); 250 251 foreach($phraseur_xml->dtc->entites as $k => $v) 252 if (!strpos(" amp lt gt quot ", $k)) 253 $trans["&$k;"] = $v; 254 $data = strtr($data, $trans); 255 } else 256 $data = html2unicode($data, true); 257 258 return array($doctype,unicode2charset($data)); 259 } 260 261 // http://doc.spip.org/@analyser_doctype 262 function analyser_doctype($data) 263 { 264 if (!preg_match(_REGEXP_DOCTYPE, $data, $r)) 265 return array(); 266 267 list($doctype,$pi,$co,$pico, $topelement, $avail,$suite) = $r; 268 269 if (!preg_match('/^"([^"]*)"\s*(.*)$/', $suite, $r)) 270 if (!preg_match("/^'([^']*)'\s*(.*)$/", $suite, $r)) 271 return array(); 272 list(,$rotlvl, $suite) = $r; 273 274 if (!$suite) { 275 if ($avail != 'SYSTEM') return array(); 276 $grammaire = $rotlvl; 277 $rotlvl = ''; 278 } else { 279 if (!preg_match('/^"([^"]*)"\s*$/', $suite, $r)) 280 if (!preg_match("/^'([^']*)'\s*$/", $suite, $r)) 281 return array(); 282 283 $grammaire = $r[1]; 284 } 285 286 return array(substr($doctype,strlen($pico)), $topelement, $avail, $grammaire, $rotlvl); 287 } 288 289 ?>
titre
Description
Corps
titre
Description
Corps
titre
Description
Corps
titre
Corps
| Généré le : Wed Nov 21 10:20:27 2007 | par Balluche grâce à PHPXref 0.7 |
|