/ecrire/public/balises.php
PHP | 2730 lines | 1019 code | 223 blank | 1488 comment | 119 complexity | ad518b176113eae9b5d556cb937931ff MD5 | raw file
Large files files are truncated, but you can click here to view the full file
- <?php
- /***************************************************************************\
- * SPIP, Systeme de publication pour l'internet *
- * *
- * Copyright (c) 2001-2014 *
- * 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. *
- \***************************************************************************/
- /**
- * Ce fichier regroupe la quasi totalité des définitions de `#BALISES` de SPIP.
- *
- * Pour chaque balise, il est possible de surcharger, dans son fichier
- * mes_fonctions.php, la fonction `balise_TOTO_dist()` par une fonction
- * `balise_TOTO()` respectant la même API : elle reçoit en entrée un objet
- * de classe `Champ`, le modifie et le retourne. Cette classe est définie
- * dans public/interfaces.
- *
- * Des balises dites «dynamiques» sont également déclarées dans le
- * répertoire ecrire/balise/
- *
- * @package SPIP\Core\Compilateur\Balises
- **/
- if (!defined('_ECRIRE_INC_VERSION')) return;
- /**
- * Retourne le code PHP d'un argument de balise s'il est présent
- *
- * @uses calculer_liste()
- * @example
- * ```
- * // Retourne le premier argument de la balise
- * // #BALISE{premier,deuxieme}
- * $arg = interprete_argument_balise(1,$p);
- * ```
- *
- * @param int $n
- * Numéro de l'argument
- * @param Champ $p
- * Pile au niveau de la balise
- * @return string|null
- * Code PHP si cet argument est présent, sinon null
- **/
- function interprete_argument_balise($n,$p) {
- if (($p->param) && (!$p->param[0][0]) && (count($p->param[0])>$n))
- return calculer_liste($p->param[0][$n],
- $p->descr,
- $p->boucles,
- $p->id_boucle);
- else
- return NULL;
- }
- //
- // Définition des balises
- //
- /**
- * Compile la balise `#NOM_SITE_SPIP` retournant le nom du site
- *
- * @balise
- * @link http://www.spip.net/4622
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_NOM_SITE_SPIP_dist($p) {
- $p->code = "\$GLOBALS['meta']['nom_site']";
- #$p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#EMAIL_WEBMASTER` retournant l'adresse courriel
- * du webmestre
- *
- * @balise
- * @link http://www.spip.net/4586
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_EMAIL_WEBMASTER_dist($p) {
- $p->code = "\$GLOBALS['meta']['email_webmaster']";
- #$p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#DESCRIPTIF_SITE_SPIP` qui retourne le descriptif
- * du site !
- *
- * @balise
- * @link http://www.spip.net/4338
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_DESCRIPTIF_SITE_SPIP_dist($p) {
- $p->code = "\$GLOBALS['meta']['descriptif_site']";
- #$p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#CHARSET` qui retourne le nom du jeu de caractères
- * utilisé par le site tel que `utf-8`
- *
- * @balise
- * @link http://www.spip.net/4331
- * @example
- * ```
- * <meta http-equiv="Content-Type" content="text/html; charset=#CHARSET" />
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_CHARSET_dist($p) {
- $p->code = "\$GLOBALS['meta']['charset']";
- #$p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#LANG_LEFT` retournant 'left' si la langue s'écrit
- * de gauche à droite, sinon 'right'
- *
- * @note
- * Peut servir à l'écriture de code CSS dans un squelette, mais
- * pour inclure un fichier css, il vaut mieux utiliser le filtre
- * `direction_css` si on le souhaite sensible à la langue utilisé.
- *
- * @balise
- * @link http://www.spip.net/4625
- * @see lang_dir()
- * @see balise_LANG_RIGHT_dist()
- * @see balise_LANG_DIR_dist()
- * @see direction_css()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_LANG_LEFT_dist($p) {
- $_lang = champ_sql('lang', $p);
- $p->code = "lang_dir($_lang, 'left','right')";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#LANG_RIGHT` retournant 'right' si la langue s'écrit
- * de gauche à droite, sinon 'left'
- *
- * @balise
- * @link http://www.spip.net/4625
- * @see lang_dir()
- * @see balise_LANG_LEFT_dist()
- * @see balise_LANG_DIR_dist()
- * @see direction_css()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_LANG_RIGHT_dist($p) {
- $_lang = champ_sql('lang', $p);
- $p->code = "lang_dir($_lang, 'right','left')";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#LANG_DIR` retournant 'ltr' si la langue s'écrit
- * de gauche à droite, sinon 'rtl'
- *
- * @balise
- * @link http://www.spip.net/4625
- * @see lang_dir()
- * @see balise_LANG_LEFT_dist()
- * @see balise_LANG_RIGHT_dist()
- * @example
- * ```
- * <html dir="#LANG_DIR" lang="#LANG"
- * xmlns="http://www.w3.org/1999/xhtml"
- * xml:lang="#LANG" class="[(#LANG_DIR)][ (#LANG)] no-js">
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_LANG_DIR_dist($p) {
- $_lang = champ_sql('lang', $p);
- $p->code = "lang_dir($_lang, 'ltr','rtl')";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#PUCE` affichant une puce
- *
- * @balise
- * @link http://www.spip.net/4628
- * @see definir_puce()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_PUCE_dist($p) {
- $p->code = "definir_puce()";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#DATE` qui retourne la date de mise en ligne
- *
- * Cette balise retourne soit le champ `date` d'une table si elle est
- * utilisée dans une boucle, sinon la date de calcul du squelette.
- *
- * @balise
- * @link http://www.spip.net/4336 Balise DATE
- * @link http://www.spip.net/1971 La gestion des dates
- * @example
- * ```
- * <td>[(#DATE|affdate_jourcourt)]</td>
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- */
- function balise_DATE_dist ($p) {
- $d = champ_sql('date', $p);
- # if ($d === "@\$Pile[0]['date']")
- # $d = "isset(\$Pile[0]['date']) ? $d : time()";
- $p->code = $d;
- return $p;
- }
- /**
- * Compile la balise `#DATE_REDAC` qui retourne la date de première publication
- *
- * Cette balise retourne le champ `date_redac` d'une table
- *
- * @balise
- * @link http://www.spip.net/3858 Balises DATE_MODIF et DATE_REDAC
- * @link http://www.spip.net/1971 La gestion des dates
- * @see balise_DATE_MODIF_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- */
- function balise_DATE_REDAC_dist ($p) {
- $d = champ_sql('date_redac', $p);
- # if ($d === "@\$Pile[0]['date_redac']")
- # $d = "isset(\$Pile[0]['date_redac']) ? $d : time()";
- $p->code = $d;
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#DATE_MODIF` qui retourne la date de dernière modification
- *
- * Cette balise retourne le champ `date_modif` d'une table
- *
- * @balise
- * @link http://www.spip.net/3858 Balises DATE_MODIF et DATE_REDAC
- * @link http://www.spip.net/1971 La gestion des dates
- * @see balise_DATE_REDAC_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- */
- function balise_DATE_MODIF_dist ($p) {
- $p->code = champ_sql('date_modif', $p);
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#DATE_NOUVEAUTES` indiquant la date de dernier envoi
- * du mail de nouveautés
- *
- * @balise
- * @link http://www.spip.net/4337 Balise DATE_NOUVEAUTES
- * @link http://www.spip.net/1971 La gestion des dates
- * @see balise_DATE_REDAC_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- */
- function balise_DATE_NOUVEAUTES_dist($p) {
- $p->code = "((\$GLOBALS['meta']['quoi_de_neuf'] == 'oui'
- AND isset(\$GLOBALS['meta']['dernier_envoi_neuf'])) ?
- \$GLOBALS['meta']['dernier_envoi_neuf'] :
- \"'0000-00-00'\")";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#DOSSIER_SQUELETTE` retournant le chemin vers le
- * répertoire de squelettes actuellement utilisé
- *
- * @balise
- * @deprecated Utiliser `#CHEMIN`
- * @link http://www.spip.net/4627
- * @see balise_CHEMIN_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- */
- function balise_DOSSIER_SQUELETTE_dist($p) {
- $code = substr(addslashes(dirname($p->descr['sourcefile'])), strlen(_DIR_RACINE));
- $p->code = "_DIR_RACINE . '$code'" .
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#SQUELETTE` retournant le chemin du squelette courant
- *
- * @balise
- * @link http://www.spip.net/4027
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- */
- function balise_SQUELETTE_dist($p) {
- $code = addslashes($p->descr['sourcefile']);
- $p->code = "'$code'" .
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#SPIP_VERSION` qui affiche la version de SPIP
- *
- * @balise
- * @see spip_version()
- * @example
- * ```
- * <meta name="generator" content="SPIP[ (#SPIP_VERSION)]" />
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- */
- function balise_SPIP_VERSION_dist($p) {
- $p->code = "spip_version()";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#NOM_SITE` qui affiche le nom du site.
- *
- * Affiche le nom du site ou sinon l'URL ou le titre de l'objet
- * Utiliser `#NOM_SITE*` pour avoir le nom du site ou rien.
- *
- * Cette balise interroge les colonnes `nom_site` ou `url_site`
- * dans la boucle la plus proche.
- *
- * @balise
- * @see calculer_url()
- * @example
- * ```
- * <a href="#URL_SITE">#NOM_SITE</a>
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_NOM_SITE_dist($p) {
- if (!$p->etoile) {
- $p->code = "supprimer_numero(calculer_url(" .
- champ_sql('url_site',$p) ."," .
- champ_sql('nom_site',$p) .
- ", 'titre', \$connect, false))";
- } else
- $p->code = champ_sql('nom_site',$p);
- $p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#NOTE` qui affiche les notes de bas de page
- *
- * @balise
- * @link http://www.spip.net/3964
- * @see calculer_notes()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_NOTES_dist($p) {
- // Recuperer les notes
- $p->code = 'calculer_notes()';
- #$p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#RECHERCHE` qui retourne le terme de recherche demandé
- *
- * Retourne un terme demandé en recherche, en le prenant dans _request()
- * sous la clé `recherche`.
- *
- * @balise
- * @example
- * ```
- * <h3>Recherche de : #RECHERCHE</h3>
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_RECHERCHE_dist($p) {
- $p->code = 'entites_html(_request("recherche"))';
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#COMPTEUR_BOUCLE` qui retourne le numéro de l’itération
- * actuelle de la boucle
- *
- * @balise
- * @link http://www.spip.net/4333
- * @see balise_TOTAL_BOUCLE_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_COMPTEUR_BOUCLE_dist($p) {
- $b = $p->nom_boucle ? $p->nom_boucle : $p->descr['id_mere'];
- if ($b === '') {
- $msg = array('zbug_champ_hors_boucle',
- array('champ' => '#COMPTEUR_BOUCLE')
- );
- erreur_squelette($msg, $p);
- } else {
- $p->code = "\$Numrows['$b']['compteur_boucle']";
- $p->boucles[$b]->cptrows = true;
- $p->interdire_scripts = false;
- return $p;
- }
- }
- /**
- * Compile la balise `#TOTAL_BOUCLE` qui retourne le nombre de résultats
- * affichés par la boucle
- *
- * @balise
- * @link http://www.spip.net/4334
- * @see balise_COMPTEUR_BOUCLE_dist()
- * @see balise_GRAND_TOTAL_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_TOTAL_BOUCLE_dist($p) {
- $b = $p->nom_boucle ? $p->nom_boucle : $p->descr['id_mere'];
- if ($b === '' || !isset($p->boucles[$b])) {
- $msg = array('zbug_champ_hors_boucle',
- array('champ' => "#$b" . 'TOTAL_BOUCLE')
- );
- erreur_squelette($msg, $p);
- } else {
- $p->code = "\$Numrows['$b']['total']";
- $p->boucles[$b]->numrows = true;
- $p->interdire_scripts = false;
- }
- return $p;
- }
- /**
- * Compile la balise `#POINTS` qui affiche la pertinence des résultats
- *
- * Retourne le calcul `points` réalisé par le critère `recherche`.
- * Cette balise nécessite donc la présence de ce critère.
- *
- * @balise
- * @link http://www.spip.net/903 Boucles et balises de recherche
- * @see critere_recherche_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_POINTS_dist($p) {
- return rindex_pile($p, 'points', 'recherche');
- }
- /**
- * Compile la balise `#POPULARITE_ABSOLUE` qui affiche la popularité absolue
- *
- * Cela correspond à la popularité quotidienne de l'article
- *
- * @balise
- * @link http://www.spip.net/1846 La popularité
- * @see balise_POPULARITE_dist()
- * @see balise_POPULARITE_MAX_dist()
- * @see balise_POPULARITE_SITE_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_POPULARITE_ABSOLUE_dist($p) {
- $p->code = 'ceil(' .
- champ_sql('popularite', $p) .
- ')';
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#POPULARITE_SITE` qui affiche la popularité du site
- *
- * La popularité du site est la somme de toutes les popularités absolues.
- *
- * @balise
- * @link http://www.spip.net/1846 La popularité
- * @see balise_POPULARITE_ABSOLUE_dist()
- * @see balise_POPULARITE_dist()
- * @see balise_POPULARITE_MAX_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_POPULARITE_SITE_dist($p) {
- $p->code = 'ceil($GLOBALS["meta"][\'popularite_total\'])';
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#POPULARITE_MAX` qui affiche la popularité maximum
- * parmis les popularités des articles
- *
- * Cela correspond à la popularité quotidienne de l'article
- *
- * @balise
- * @link http://www.spip.net/1846 La popularité
- * @see balise_POPULARITE_ABSOLUE_dist()
- * @see balise_POPULARITE_dist()
- * @see balise_POPULARITE_SITE_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_POPULARITE_MAX_dist($p) {
- $p->code = 'ceil($GLOBALS["meta"][\'popularite_max\'])';
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#VALEUR` retournant le champ `valeur`
- *
- * Utile dans une boucle DATA pour retourner une valeur.
- *
- * @balise
- * @link http://www.spip.net/5546 #CLE et #VALEUR
- * @see table_valeur()
- * @example
- * ```
- * #VALEUR renvoie le champ valeur
- * #VALEUR{x} renvoie #VALEUR|table_valeur{x},
- * équivalent à #X (si X n'est pas une balise spéficique à SPIP)
- * #VALEUR{a/b} renvoie #VALEUR|table_valeur{a/b}
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_VALEUR_dist($p) {
- $b = $p->nom_boucle ? $p->nom_boucle : $p->id_boucle;
- $p->code = index_pile($p->id_boucle, 'valeur', $p->boucles, $b);;
- if (($v = interprete_argument_balise(1,$p))!==NULL){
- $p->code = 'table_valeur('.$p->code.', '.$v.')';
- }
- $p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#EXPOSE` qui met en évidence l'élément sur lequel
- * la page se trouve
- *
- * Expose dans une boucle l'élément de la page sur laquelle on se trouve,
- * en retournant `on` si l'élément correspond à la page, une chaîne vide sinon.
- *
- * On peut passer les paramètres à faire retourner par la balise.
- *
- * @example
- * ```
- * <a href="#URL_ARTICLE"[ class="(#EXPOSE)"]>
- * <a href="#URL_ARTICLE"[ class="(#EXPOSE{actif})"]>
- * <a href="#URL_ARTICLE"[ class="(#EXPOSE{on,off})"]>
- * ```
- *
- * @balise
- * @link http://www.spip.net/2319 Exposer un article
- * @uses calculer_balise_expose()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_EXPOSE_dist($p) {
- $on = "'on'";
- $off= "''";
- if (($v = interprete_argument_balise(1,$p))!==NULL){
- $on = $v;
- if (($v = interprete_argument_balise(2,$p))!==NULL)
- $off = $v;
- }
- return calculer_balise_expose($p, $on, $off);
- }
- /**
- * Calcul de la balise expose
- *
- * @see calcul_exposer()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @param string $on
- * Texte à afficher si l'élément est exposé (code à écrire tel que "'on'")
- * @param string $off
- * Texte à afficher si l'élément n'est pas exposé (code à écrire tel que "''")
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function calculer_balise_expose($p, $on, $off)
- {
- $b = $p->nom_boucle ? $p->nom_boucle : $p->id_boucle;
- $key = $p->boucles[$b]->primary;
- $type = $p->boucles[$p->id_boucle]->primary;
- $desc = $p->boucles[$b]->show;
- $connect = sql_quote($p->boucles[$b]->sql_serveur);
- if (!$key) {
- $msg = array('zbug_champ_hors_boucle', array('champ' => '#EXPOSER'));
- erreur_squelette($msg, $p);
- }
- // Ne pas utiliser champ_sql, on jongle avec le nom boucle explicite
- $c = index_pile($p->id_boucle, $type, $p->boucles);
- if (isset($desc['field']['id_parent'])) {
- $parent = 0; // pour if (!$parent) dans calculer_expose
- } elseif (isset($desc['field']['id_rubrique'])) {
- $parent = index_pile($p->id_boucle, 'id_rubrique', $p->boucles, $b);
- } elseif (isset($desc['field']['id_groupe'])) {
- $parent = index_pile($p->id_boucle, 'id_groupe', $p->boucles, $b);
- } else $parent = "''";
- $p->code = "(calcul_exposer($c, '$type', \$Pile[0], $parent, '$key', $connect) ? $on : $off)";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#DEBUT_SURLIGNE` qui permettait le surlignage
- * des mots d'une recherche
- *
- * @note
- * Cette balise n'a plus d'effet depuis r9343
- *
- * @balise
- * @see balise_FIN_SURLIGNE_dist()
- * @deprecated Utiliser les classes CSS `surlignable` ou `pas_surlignable`
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_DEBUT_SURLIGNE_dist($p) {
- include_spip('inc/surligne');
- $p->code = "'<!-- " . MARQUEUR_SURLIGNE . " -->'";
- return $p;
- }
- /**
- * Compile la balise `#FIN_SURLIGNE` qui arrêtait le surlignage
- * des mots d'une recherche
- *
- * @note
- * Cette balise n'a plus d'effet depuis r9343
- *
- * @balise
- * @see balise_DEBUT_SURLIGNE_dist()
- * @deprecated Utiliser les classes CSS `surlignable` ou `pas_surlignable`
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_FIN_SURLIGNE_dist($p) {
- include_spip('inc/surligne');
- $p->code = "'<!-- " . MARQUEUR_FSURLIGNE . "-->'";
- return $p;
- }
- /**
- * Compile la balise `#INTRODUCTION`
- *
- * Retourne une introduction d'un objet éditorial, c'est à dire les 600
- * premiers caractères environ du champ 'texte' de l'objet ou le contenu
- * indiqué entre `<intro>` et `</intro>` de ce même champ.
- *
- * Pour les articles, l'introduction utilisée est celle du champ `descriptif`
- * s'il est renseigné, sinon il est pris dans les champs `chapo` et `texte` et
- * est par défaut limité à 500 caractères.
- *
- * Pour les rubriques, l'introduction utilisée est celle du champ `descriptif`
- * s'il est renseigné, sinon du champ texte.
- *
- * La balise accèpte 1 paramètre indiquant la longueur en nombre de caractères
- * de l'introduction.
- *
- * @see filtre_introduction_dist()
- * @example
- * ```
- * #INTRODUCTION
- * #INTRODUCTION{300}
- * ```
- *
- * @balise
- * @link http://www.spip.net/@introduction
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_INTRODUCTION_dist($p) {
- $type = $p->type_requete;
- $_texte = champ_sql('texte', $p);
- $_descriptif = ($type == 'articles' OR $type == 'rubriques') ? champ_sql('descriptif', $p) : "''";
- if ($type == 'articles') {
- $_chapo = champ_sql('chapo', $p);
- $_texte = "(strlen($_descriptif))
- ? ''
- : $_chapo . \"\\n\\n\" . $_texte";
- }
- // longueur en parametre, ou valeur par defaut
- $longueur_defaut = objet_info($type,'introduction_longueur');
- if (!$longueur_defaut)
- $longueur_defaut = 600;
- $_suite = 'null';
- $_longueur = $longueur_defaut;
- if (($v = interprete_argument_balise(1,$p))!==NULL) {
- $_longueur = 'is_numeric('.$v.')?intval('.$v.'):'.$longueur_defaut;
- $_suite = '!is_numeric('.$v.')?'.$v.':null';
- }
- if (($v2 = interprete_argument_balise(2,$p))!==NULL) {
- $_suite = $v2;
- }
- $f = chercher_filtre('introduction');
- $p->code = "$f($_descriptif, $_texte, $_longueur, \$connect, $_suite)";
- #$p->interdire_scripts = true;
- $p->etoile = '*'; // propre est deja fait dans le calcul de l'intro
- return $p;
- }
- /**
- * Compile la balise `#LANG` qui affiche la langue de l'objet (ou d'une boucle supérieure),
- * et à defaut la langue courante
- *
- * La langue courante est celle du site ou celle qui a été passée dans l'URL par le visiteur.
- * L'étoile `#LANG*` n'affiche rien si aucune langue n'est trouvée dans le SQL ou le contexte.
- *
- * @balise
- * @link http://www.spip.net/3864
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_LANG_dist ($p) {
- $_lang = champ_sql('lang', $p);
- if (!$p->etoile)
- $p->code = "spip_htmlentities($_lang ? $_lang : \$GLOBALS['spip_lang'])";
- else
- $p->code = "spip_htmlentities($_lang)";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#LESAUTEURS` chargée d'afficher la liste des auteurs d'un objet
- *
- * - Soit le champ `lesauteurs` existe dans la table et à ce moment là,
- * la balise retourne son contenu,
- * - soit la balise appelle le modele `lesauteurs.html` en lui passant
- * le couple `objet` et `id_objet` dans son environnement.
- *
- * @balise
- * @link http://www.spip.net/3966 Description de la balise
- * @link http://www.spip.net/902 Description de la boucle ARTICLES
- * @link http://www.spip.net/911 Description de la boucle SYNDIC_ARTICLES
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- */
- function balise_LESAUTEURS_dist ($p) {
- // Cherche le champ 'lesauteurs' dans la pile
- $_lesauteurs = champ_sql('lesauteurs', $p, false);
- // Si le champ n'existe pas (cas de spip_articles), on applique
- // le modele lesauteurs.html en passant id_article dans le contexte;
- // dans le cas contraire on prend le champ 'lesauteurs'
- // (cf extension sites/)
- if ($_lesauteurs
- AND $_lesauteurs != '@$Pile[0][\'lesauteurs\']') {
- $p->code = "safehtml($_lesauteurs)";
- // $p->interdire_scripts = true;
- } else {
- if(!$p->id_boucle){
- $connect = '';
- $objet = 'article';
- $id_table_objet = 'id_article';
- }
- else{
- $b = $p->nom_boucle ? $p->nom_boucle : $p->id_boucle;
- $connect = $p->boucles[$b]->sql_serveur;
- $type_boucle = $p->boucles[$b]->type_requete;
- $objet = objet_type($type_boucle);
- $id_table_objet = id_table_objet($type_boucle);
- }
- $c = memoriser_contexte_compil($p);
- $p->code = sprintf(CODE_RECUPERER_FOND, "'modeles/lesauteurs'",
- "array('objet'=>'".$objet.
- "','id_objet' => ".champ_sql($id_table_objet, $p) .
- ",'$id_table_objet' => ".champ_sql($id_table_objet, $p) .
- ($objet=='article'?"":",'id_article' => ".champ_sql('id_article', $p)).
- ")",
- "'trim'=>true, 'compil'=>array($c)",
- _q($connect));
- $p->interdire_scripts = false; // securite apposee par recuperer_fond()
- }
- return $p;
- }
- /**
- * Compile la balise `#RANG` chargée d'afficher le numéro de l'objet
- *
- * Affiche le « numero de l'objet ». Soit `1` quand on a un titre `1. Premier article`.
- *
- * Ceci est transitoire afin de préparer une migration vers un vrai système de
- * tri des articles dans une rubrique (et plus si affinités).
- * La balise permet d'extraire le numero masqué par le filtre `supprimer_numero`.
- *
- * La balise recupère le champ declaré dans la définition `table_titre`
- * de l'objet, ou à defaut du champ `titre`
- *
- * Si un champ `rang` existe, il est pris en priorité.
- *
- * @balise
- * @link http://www.spip.net/5495
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- */
- function balise_RANG_dist($p) {
- $b = index_boucle($p);
- if ($b === '') {
- $msg = array('zbug_champ_hors_boucle',
- array('champ' => '#RANG')
- );
- erreur_squelette($msg, $p);
- }
- else {
- // chercher d'abord un champ sql rang (mais pas dans le env : defaut '' si on trouve pas de champ sql)
- // dans la boucle immediatement englobante uniquement
- // sinon on compose le champ calcule
- $_rang = champ_sql('rang', $p, '', false);
- // si pas trouve de champ sql rang :
- if (!$_rang OR $_rang == "''"){
- $boucle = &$p->boucles[$b];
- $trouver_table = charger_fonction('trouver_table','base');
- $desc = $trouver_table($boucle->id_table);
- $_titre = ''; # où extraire le numero ?
- if (isset($desc['titre'])){
- $t=$desc['titre'];
- if (preg_match(';(^|,)([^,]*titre)(,|$);',$t,$m)){
- $m = preg_replace(",as\s+titre$,i","",$m[2]);
- $m = trim($m);
- if ($m!="''"){
- if (!preg_match(",\W,",$m))
- $m = $boucle->id_table . ".$m";
- $m .= " AS titre_rang";
- $boucle->select[] = $m;
- $_titre = '$Pile[$SP][\'titre_rang\']';
- }
- }
- }
- if (!$_titre)
- $_titre = champ_sql('titre', $p);
- $_rang = "recuperer_numero($_titre)";
- }
- $p->code = $_rang;
- $p->interdire_scripts = false;
- }
- return $p;
- }
- /**
- * Compile la balise `#POPULARITE` qui affiche la popularité relative.
- *
- * C'est à dire le pourcentage de la fréquentation de l'article
- * (la popularité absolue) par rapport à la popularité maximum.
- *
- * @balise
- * @link http://www.spip.net/1846 La popularité
- * @see balise_POPULARITE_ABSOLUE_dist()
- * @see balise_POPULARITE_MAX_dist()
- * @see balise_POPULARITE_SITE_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_POPULARITE_dist ($p) {
- $_popularite = champ_sql('popularite', $p);
- $p->code = "(ceil(min(100, 100 * $_popularite
- / max(1 , 0 + \$GLOBALS['meta']['popularite_max']))))";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Code de compilation pour la balise `#PAGINATION`
- *
- * Le code produit est trompeur, car les modèles ne fournissent pas Pile[0].
- * On produit un appel à `_request` si on ne l'a pas, mais c'est inexact:
- * l'absence peut-être due à une faute de frappe dans le contexte inclus.
- */
- define('CODE_PAGINATION',
- '%s($Numrows["%s"]["grand_total"],
- %s,
- isset($Pile[0][%4$s])?$Pile[0][%4$s]:intval(_request(%4$s)),
- %5$s, %6$s, %7$s, %8$s, array(%9$s))');
- /**
- * Compile la balise `#PAGINATION` chargée d'afficher une pagination
- *
- * Elle charge le modèle `pagination.html` (par défaut), mais un paramètre
- * permet d'indiquer d'autres modèles. `#PAGINATION{nom}` utilisera le
- * modèle `pagination_nom.html`.
- *
- * Cette balise nécessite le critère `pagination` sur la boucle où elle
- * est utilisée.
- *
- * @balise
- * @link http://www.spip.net/3367 Le système de pagination
- * @see filtre_pagination_dist()
- * @see critere_pagination_dist()
- * @see balise_ANCRE_PAGINATION_dist()
- * @example
- * ```
- * [<p class="pagination">(#PAGINATION{prive})</p>]
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @param string $liste
- * Afficher ou non les liens de pagination (variable de type `string`
- * car code à faire écrire au compilateur) :
- * - `true` pour les afficher
- * - `false` pour afficher uniquement l'ancre.
- * @return Champ
- * Pile complétée par le code à générer
- */
- function balise_PAGINATION_dist($p, $liste='true') {
- $b = $p->nom_boucle ? $p->nom_boucle : $p->descr['id_mere'];
- // s'il n'y a pas de nom de boucle, on ne peut pas paginer
- if ($b === '') {
- $msg = array('zbug_champ_hors_boucle',
- array('champ' => $liste ? 'PAGINATION' : 'ANCRE_PAGINATION')
- );
- erreur_squelette($msg, $p);
- return $p;
- }
- // s'il n'y a pas de mode_partie, c'est qu'on se trouve
- // dans un boucle recursive ou qu'on a oublie le critere {pagination}
- if (!$p->boucles[$b]->mode_partie) {
- if (!$p->boucles[$b]->table_optionnelle) {
- $msg = array('zbug_pagination_sans_critere',
- array('champ' => '#PAGINATION')
- );
- erreur_squelette($msg, $p);
- }
- return $p;
- }
- // a priori true
- // si false, le compilo va bloquer sur des syntaxes avec un filtre sans argument qui suit la balise
- // si true, les arguments simples (sans truc=chose) vont degager
- $_contexte = argumenter_inclure($p->param, true, $p, $p->boucles, $p->id_boucle, false, false);
- if (count($_contexte)){
- list($key,$val) = each($_contexte);
- if (is_numeric($key)){
- array_shift($_contexte);
- $__modele = interprete_argument_balise(1,$p);
- }
- }
- if (count($_contexte)){
- $code_contexte = implode(',',$_contexte);
- }
- else
- $code_contexte = '';
- $connect = $p->boucles[$b]->sql_serveur;
- $pas = $p->boucles[$b]->total_parties;
- $f_pagination = chercher_filtre('pagination');
- $type = $p->boucles[$b]->modificateur['debut_nom'];
- $modif = ($type[0]!=="'") ? "'debut'.$type"
- : ("'debut" .substr($type,1));
- $p->code = sprintf(CODE_PAGINATION, $f_pagination, $b, $type, $modif, $pas, $liste, ((isset($__modele) and $__modele) ? $__modele : "''"), _q($connect), $code_contexte);
- $p->boucles[$b]->numrows = true;
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#ANCRE_PAGINATION` chargée d'afficher l'ancre
- * de la pagination
- *
- * Cette ancre peut ainsi être placée au-dessus la liste des éléments
- * de la boucle alors qu'on mettra les liens de pagination en-dessous de
- * cette liste paginée.
- *
- * Cette balise nécessite le critère `pagination` sur la boucle où elle
- * est utilisée.
- *
- * @balise
- * @link http://www.spip.net/3367 Le système de pagination
- * @link http://www.spip.net/4328 Balise ANCRE_PAGINATION
- * @see critere_pagination_dist()
- * @see balise_PAGINATION_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_ANCRE_PAGINATION_dist($p) {
- if ($f = charger_fonction('PAGINATION', 'balise', true))
- return $f($p, $liste='false');
- else return NULL; // ou une erreur ?
- }
- /**
- * Compile la balise `#GRAND_TOTAL` qui retourne le nombre total de résultats
- * d'une boucle
- *
- * Cette balise set équivalente à `#TOTAL_BOUCLE` sauf pour les boucles paginées.
- * Dans ce cas elle indique le nombre total d'éléments répondant aux critères
- * hors pagination.
- *
- * @balise
- * @see balise_GRAND_TOTAL_dist()
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_GRAND_TOTAL_dist($p) {
- $b = $p->nom_boucle ? $p->nom_boucle : $p->descr['id_mere'];
- if ($b === '' || !isset($p->boucles[$b])) {
- $msg = array('zbug_champ_hors_boucle',
- array('champ' => "#$b" . 'TOTAL_BOUCLE')
- );
- erreur_squelette($msg, $p);
- } else {
- $p->code = "(isset(\$Numrows['$b']['grand_total'])
- ? \$Numrows['$b']['grand_total'] : \$Numrows['$b']['total'])";
- $p->boucles[$b]->numrows = true;
- $p->interdire_scripts = false;
- }
- return $p;
- }
- /**
- * Compile la balise `#SELF` qui retourne l’URL de la page appelée.
- *
- * Cette URL est nettoyée des variables propres à l’exécution de SPIP
- * tel que `var_mode`.
- *
- * @note
- * Attention dans un `INCLURE()` ou une balise dynamique, on n'a pas le droit de
- * mettre en cache `#SELF` car il peut correspondre à une autre page (attaque XSS)
- * (Dans ce cas faire <INCLURE{self=#SELF}> pour différencier les caches.)
- *
- * @balise
- * @link http://www.spip.net/4574
- * @example
- * ```
- * <a href="[(#SELF|parametre_url{id_mot,#ID_MOT})]">...
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_SELF_dist($p) {
- $p->code = 'self()';
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#CHEMIN` qui cherche un fichier dans les chemins
- * connus de SPIP et retourne son chemin complet depuis la racine
- *
- * Signature : `#CHEMIN{chemin/vers/fichier.ext}`
- *
- * Retourne une chaîne vide si le fichier n'est pas trouvé.
- *
- * @balise
- * @link http://www.spip.net/4332
- * @see find_in_path() Recherche de chemin
- * @example
- * ```
- * [<script type="text/javascript" src="(#CHEMIN{javascript/jquery.flot.js})"></script>]
- * [<link rel="stylesheet" href="(#CHEMIN{css/perso.css}|direction_css)" type="text/css" />]
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_CHEMIN_dist($p) {
- $arg = interprete_argument_balise(1,$p);
- if (!$arg) {
- $msg = array('zbug_balise_sans_argument', array('balise' => ' CHEMIN'));
- erreur_squelette($msg, $p);
- } else
- $p->code = 'find_in_path(' . $arg .')';
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#CHEMIN_IMAGE` qui cherche une image dans le thème
- * de l'espace privé utilisé par SPIP et retourne son chemin complet depuis
- * la racine
- *
- * Signature : `#CHEMIN_IMAGE{image.png}`
- *
- * Retourne une chaîne vide si le fichier n'est pas trouvé.
- *
- * @balise
- * @see chemin_image()
- * @example
- * ```
- * #CHEMIN_IMAGE{article-24.png}
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_CHEMIN_IMAGE_dist($p) {
- $arg = interprete_argument_balise(1,$p);
- if (!$arg) {
- $msg = array('zbug_balise_sans_argument', array('balise' => ' CHEMIN_IMAGE'));
- erreur_squelette($msg, $p);
- } else $p->code = 'chemin_image(' . $arg .')';
- #$p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#ENV` qui permet de récupérer le contexte d'environnement
- * transmis à un squelette.
- *
- * La syntaxe `#ENV{toto, valeur par defaut}`
- * renverra `valeur par defaut` si `$toto` est vide.
- *
- * La recherche de la clé s'appuyant sur la fonction `table_valeur`
- * il est possible de demander un sous élément d'un tableau :
- * `#ENV{toto/sous/element, valeur par defaut}` retournera l'équivalent de
- * `#ENV{toto}|table_valeur{sous/element}` c'est-à-dire en quelque sorte
- * `$env['toto']['sous']['element']` s'il existe, sinon la valeur par défaut.
- *
- * Si le tableau est vide on renvoie `''` (utile pour `#SESSION`)
- *
- * Enfin, la balise utilisée seule `#ENV` retourne le tableau complet
- * de l'environnement. À noter que ce tableau est retourné sérialisé.
- *
- * En standard est appliqué le filtre `entites_html`, mais si l'étoile est
- * utilisée pour désactiver les filtres par défaut, par exemple avec
- * `[(#ENV*{toto})]` , il *faut* s'assurer de la sécurité
- * anti-javascript, par exemple en filtrant avec `safehtml` : `[(#ENV*{toto}|safehtml)]`
- *
- *
- * @param Champ $p
- * Pile ; arbre de syntaxe abstrait positionné au niveau de la balise.
- * @param array $src
- * Tableau dans lequel chercher la clé demandée en paramètre de la balise.
- * Par defaut prend dans le contexte du squelette.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- **/
- function balise_ENV_dist($p, $src = NULL) {
- // cle du tableau desiree
- $_nom = interprete_argument_balise(1,$p);
- // valeur par defaut
- $_sinon = interprete_argument_balise(2,$p);
-
- // $src est un tableau de donnees sources eventuellement transmis
- // en absence, on utilise l'environnement du squelette $Pile[0]
-
- if (!$_nom) {
- // cas de #ENV sans argument : on retourne le serialize() du tableau
- // une belle fonction [(#ENV|affiche_env)] serait pratique
- if ($src) {
- $p->code = '(is_array($a = ('.$src.')) ? serialize($a) : "")';
- } else {
- $p->code = '@serialize($Pile[0])';
- }
- } else {
- if (!$src) {
- $src = '@$Pile[0]';
- }
- if ($_sinon) {
- $p->code = "sinon(table_valeur($src, (string)$_nom, null), $_sinon)";
- } else {
- $p->code = "table_valeur($src, (string)$_nom, null)";
- }
- }
- #$p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#CONFIG` qui retourne une valeur de configuration
- *
- * Cette balise appelle la fonction `lire_config()` pour obtenir les
- * configurations du site.
- *
- * Par exemple `#CONFIG{gerer_trad}` donne 'oui ou 'non' selon le réglage.
- *
- * Le 3ème argument permet de contrôler la sérialisation du résultat
- * (mais ne sert que pour le dépot `meta`) qui doit parfois désérialiser,
- * par exemple avec `|in_array{#CONFIG{toto,#ARRAY,1}}`. Ceci n'affecte
- * pas d'autres dépots et `|in_array{#CONFIG{toto/,#ARRAY}}` sera
- * équivalent.
- *
- * Òn peut appeler d'autres tables que `spip_meta` avec un
- * `#CONFIG{/infos/champ,defaut}` qui lit la valeur de `champ`
- * dans une table des meta qui serait `spip_infos`
- *
- * @balise
- * @link http://www.spip.net/4335
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- */
- function balise_CONFIG_dist($p) {
- if (!$arg = interprete_argument_balise(1,$p)) {
- $arg = "''";
- }
- $_sinon = interprete_argument_balise(2,$p);
- $_unserialize = sinon(interprete_argument_balise(3,$p),"false");
- $p->code = '(include_spip(\'inc/config\')?lire_config(' . $arg . ',' .
- ($_sinon && $_sinon != "''" ? $_sinon : 'null') . ',' . $_unserialize . "):'')";
- return $p;
- }
- /**
- * Compile la balise `#CONNECT` qui retourne le nom du connecteur
- * de base de données
- *
- * Retourne le nom du connecteur de base de données utilisé (le nom
- * du fichier `config/xx.php` sans l'extension, utilisé pour calculer
- * les données du squelette).
- *
- * Retourne `NULL` si le connecteur utilisé est celui par défaut de SPIP
- * (connect.php), sinon retourne son nom.
- *
- * @balise
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- */
- function balise_CONNECT_dist($p) {
- $p->code = '($connect ? $connect : NULL)';
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#SESSION` qui permet d’accéder aux informations
- * liées au visiteur authentifié et de différencier automatiquement
- * le cache en fonction du visiteur.
- *
- * Cette balise est un tableau des données du visiteur (nom, email etc).
- * Si elle est invoquée, elle lève un drapeau dans le fichier cache, qui
- * permet à public/cacher de créer un cache différent par visiteur
- *
- * @balise
- * @link http://www.spip.net/3979
- * @see balise_AUTORISER_dist()
- * @see balise_SESSION_SET_dist()
- * @example
- * ```
- * #SESSION{nom}
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- **/
- function balise_SESSION_dist($p) {
- $p->descr['session'] = true;
- $f = function_exists('balise_ENV')
- ? 'balise_ENV'
- : 'balise_ENV_dist';
- $p = $f($p, '$GLOBALS["visiteur_session"]');
- return $p;
- }
- /**
- * Compile la balise `#SESSION_SET` qui d’insérer dans la session
- * des données supplémentaires
- *
- * @balise
- * @link http://www.spip.net/3984
- * @see balise_AUTORISER_dist()
- * @see balise_SESSION_SET_dist()
- * @example
- * ```
- * #SESSION_SET{x,y} ajoute x=y dans la session du visiteur
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- **/
- function balise_SESSION_SET_dist($p) {
- $_nom = interprete_argument_balise(1,$p);
- $_val = interprete_argument_balise(2,$p);
- if (!$_nom OR !$_val) {
- $err_b_s_a = array('zbug_balise_sans_argument', array('balise' => 'SESSION_SET'));
- erreur_squelette($err_b_s_a, $p);
- } else $p->code = '(include_spip("inc/session") AND session_set('.$_nom.','.$_val.'))';
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#EVAL` qui évalue un code PHP
- *
- * À utiliser avec précautions !
- *
- * @balise
- * @link http://www.spip.net/4587
- * @example
- * ```
- * #EVAL{6+9}
- * #EVAL{_DIR_IMG_PACK}
- * #EVAL{'date("Y-m-d")'}
- * #EVAL{$_SERVER['REQUEST_URI']}
- * #EVAL{'str_replace("r","z", "roger")'} (attention les "'" sont interdits)
- * ```
- *
- * @note
- * `#EVAL{code}` produit `eval('return code;')`
- * mais si le code est une expression sans balise, on se dispense
- * de passer par une construction si compliquée, et le code est
- * passé tel quel (entre parenthèses, et protégé par interdire_scripts)
- *
- * @param Champ $p
- * Pile au niveau de la balise.
- * @return Champ
- * Pile completée du code PHP d'exécution de la balise
- **/
- function balise_EVAL_dist($p) {
- $php = interprete_argument_balise(1,$p);
- if ($php) {
- # optimisation sur les #EVAL{une expression sans #BALISE}
- # attention au commentaire "// x signes" qui precede
- if (preg_match(",^([[:space:]]*//[^\n]*\n)'([^']+)'$,ms",
- $php,$r))
- $p->code = /* $r[1]. */'('.$r[2].')';
- else
- $p->code = "eval('return '.$php.';')";
- } else {
- $msg = array('zbug_balise_sans_argument', array('balise' => ' EVAL'));
- erreur_squelette($msg, $p);
- }
- #$p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#CHAMP_SQL` qui renvoie la valeur d'un champ SQL
- *
- * Signature : `#CHAMP_SQL{champ}`
- *
- * Cette balise permet de récupérer par exemple un champ `notes` dans une table
- * SQL externe (impossible avec la balise `#NOTES` qui est une balise calculée).
- *
- * Ne permet pas de passer une expression comme argument, qui ne peut
- * être qu'un texte statique !
- *
- * @balise
- * @link http://www.spip.net/4041
- * @see champ_sql()
- * @example
- * ```
- * #CHAMP_SQL{notes}
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_CHAMP_SQL_dist($p){
- if ($p->param
- AND isset($p->param[0][1][0])
- AND $champ = ($p->param[0][1][0]->texte))
- $p->code = champ_sql($champ, $p);
- else {
- $err_b_s_a = array('zbug_balise_sans_argument', array('balise' => ' URL_'));
- erreur_squelette($err_b_s_a, $p);
- }
- #$p->interdire_scripts = true;
- return $p;
- }
- /**
- * Compile la balise `#VAL` qui retourne simplement le premier argument
- * qui lui est transmis
- *
- * Cela permet d'appliquer un filtre à une chaîne de caractère
- *
- * @balise
- * @link http://www.spip.net/4026
- * @example
- * ```
- * #VAL retourne ''
- * #VAL{x} retourne 'x'
- * #VAL{1,2} renvoie '1' (2 est considéré comme un autre paramètre)
- * #VAL{'1,2'} renvoie '1,2'
- * [(#VAL{a_suivre}|bouton_spip_rss)]
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_VAL_dist($p){
- $p->code = interprete_argument_balise(1,$p);
- if (!strlen($p->code))
- $p->code = "''";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#NOOP`, alias (déprécié) de `#VAL`
- *
- * Alias pour regler #948. Ne plus utiliser.
- *
- * @balise
- * @see balise_VAL_dist()
- * @deprecated Utiliser #VAL
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_NOOP_dist($p) { return balise_VAL_dist($p); }
- /**
- * Compile la balise `#REM` servant à commenter du texte
- *
- * Retourne toujours une chaîne vide.
- *
- * @balise
- * @link http://www.spip.net/4578
- * @example
- * ```
- * [(#REM)
- * Ceci est une remarque ou un commentaire,
- * non affiché dans le code généré
- * ]
- * ```
- *
- * @note
- * La balise `#REM` n'empêche pas l'exécution des balises SPIP contenues
- * dedans (elle ne sert pas à commenter du code pour empêcher son
- * exécution).
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_REM_dist($p) {
- $p->code="''";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#HTTP_HEADER` envoyant des entêtes de retour HTTP
- *
- * Doit être placée en tête de fichier et ne fonctionne pas dans une
- * inclusion.
- *
- * @balise
- * @link http://www.spip.net/4631
- * @example
- * ```
- * #HTTP_HEADER{Content-Type: text/csv; charset=#CHARSET}
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_HTTP_HEADER_dist($p) {
- $header = interprete_argument_balise(1,$p);
- if (!$header) {
- $err_b_s_a = array('zbug_balise_sans_argument', array('balise' => 'HTTP_HEADER'));
- erreur_squelette($err_b_s_a, $p);
- } else $p->code = "'<'.'?php header(\"' . "
- . $header
- . " . '\"); ?'.'>'";
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#FILTRE` qui exécute un filtre à l'ensemble du squelette
- * une fois calculé.
- *
- * Le filtrage se fait au niveau du squelette, sans s'appliquer aux `<INCLURE>`.
- * Plusieurs filtres peuvent être indiqués, séparés par des barres verticales `|`
- *
- * @balise
- * @link http://www.spip.net/4894
- * @example
- * ```
- * #FILTRE{compacte_head}
- * #FILTRE{supprimer_tags|filtrer_entites|trim}
- * ```
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_FILTRE_dist($p) {
- if ($p->param) {
- $args = array();
- foreach ($p->param as $i => $ignore)
- $args[] = interprete_argument_balise($i+1,$p);
- $p->code = "'<' . '"
- .'?php header("X-Spip-Filtre: \'.'
- .join('.\'|\'.', $args)
- . " . '\"); ?'.'>'";
- $p->interdire_scripts = false;
- return $p;
- }
- }
- /**
- * Compile la balise `#CACHE` definissant la durée de validité du cache du squelette
- *
- * Signature : `#CACHE{duree[,type]}`
- *
- * Le premier argument est la durée en seconde du cache. Le second
- * (par défaut `statique`) indique le type de cache :
- *
- * - `cache-client` autorise gestion du IF_MODIFIED_SINCE
- * - `statique` ne respecte pas l'invalidation par modif de la base
- * (mais s'invalide tout de même à l'expiration du delai)
- *
- * @balise
- * @see ecrire/public/cacher.php
- * @link http://www.spip.net/4330
- * @example
- * ```
- * #CACHE{24*3600}
- * #CACHE{24*3600, cache-client}
- * #CACHE{0} pas de cache
- * ```
- * @note
- * En absence de cette balise la durée est du cache est donné
- * par la constante `_DUREE_CACHE_DEFAUT`
- *
- * @param Champ $p
- * Pile au niveau de la balise
- * @return Champ
- * Pile complétée par le code à générer
- **/
- function balise_CACHE_dist($p) {
- if ($p->param) {
- $duree = valeur_numerique($p->param[0][1][0]->texte);
- // noter la duree du cache dans un entete proprietaire
- $code = '\'<'.'?php header("X-Spip-Cache: '
- . $duree
- . '"); ?'.'>\'';
- // Remplir le header Cache-Control
- // cas #CACHE{0}
- if ($duree == 0)
- $code .= '.\'<'
- .'?php header("Cache-Control: no-cache, must-revalidate"); ?'
- .'><'
- .'?php header("Pragma: no-cache"); ?'
- .'>\'';
- // recuperer les parametres suivants
- $i = 1;
- while (isset($p->param[0][++$i])) {
- $pa = ($p->param[0][$i][0]->texte);
- if ($pa == 'cache-client'
- AND $duree > 0) {
- $code .= '.\'<'.'?php header("Cache-Control: max-age='
- . $duree
- . '"); ?'.'>\'';
- // il semble logique, si on cache-client, de ne pas invalider
- $pa = 'statique';
- }
- if ($pa == 'statique'
- AND $duree > 0)
- $code .= '.\'<'.'?php header("X-Spip-Statique: oui"); ?'.'>\'';
- }
- } else $code = "''";
- $p->code = $code;
- $p->interdire_scripts = false;
- return $p;
- }
- /**
- * Compile la balise `#INSERT_HEAD` permettant d'insérer du contenu dans
- * le `<head>` d'une page HTML
- *
- * La balise permet aux plugins d'insérer des styles, js ou autre
- * dans l'entête sans modification du squelette.
- * Les css doivent être inserées de préférence par `#INSERT_HEAD_CSS`
- * pour en faciliter la sur…
Large files files are truncated, but you can click here to view the full file