source: spip-zone/_plugins_/fabrique/fabrique_fonctions.php @ 65834

Last change on this file since 65834 was 65834, checked in by marcimat@…, 9 years ago

Éviter une notice PHP

File size: 31.1 KB
Line 
1<?php
2
3/**
4 * Fonctions utiles pour les squelettes de la fabrique
5 *
6 * @package SPIP\Fabrique\Fonctions
7**/
8
9if (!defined("_ECRIRE_INC_VERSION")) return;
10
11
12/**
13 * Déterminer le répertoire de travail
14 * de la Fabrique.
15 *
16 * Dans :
17 * - plugins/fabrique_auto si possible, sinon dans
18 * - tmp/cache/fabrique
19 *
20 * @return string
21 *     Le chemin de destination depuis la racine de SPIP.
22**/
23function fabrique_destination() {
24        static $destination = null;
25        if (is_null($destination)) {
26                if (is_writable(_DIR_PLUGINS . rtrim(FABRIQUE_DESTINATION_PLUGINS, '/'))) {
27                        $destination = _DIR_PLUGINS . FABRIQUE_DESTINATION_PLUGINS;
28                } else {
29                        sous_repertoire(_DIR_CACHE, rtrim(FABRIQUE_DESTINATION_CACHE, '/'));
30                        $destination = _DIR_CACHE . FABRIQUE_DESTINATION_CACHE;
31                }
32        }
33        return $destination;
34}
35
36
37/**
38 * Crée l'arborescence manquante
39 *
40 * Crée tous les répertoires manquants dans une arborescence donnée.
41 * Les répertoires sont séparés par des '/'
42 *
43 * @example
44 *     sous_repertoire_complet('a/b/c/d');
45 *     appelle sous_repertoire() autant de fois que nécéssaire.
46 *
47 * @param string $arbo
48 *     Arborescence, tel que 'prive/squelettes/contenu'
49 * @return void
50**/
51function sous_repertoire_complet($arbo) {
52        $a = explode('/', $arbo);
53        if ($a[0] == '.' OR $a[0] == '..') {
54                $base = $a[0] . '/' . $a[1];
55                array_shift($a);
56                array_shift($a);
57        } else {
58                $base = $a[0];
59                array_shift($a);
60        }
61
62        foreach ($a as $dir) {
63                $base .= '/' . $dir;
64                sous_repertoire($base);
65        }
66}
67
68
69/**
70 * Concatène en utilisant implode, un tableau, de maniere récursive
71 *
72 * @param array $tableau
73 *     Tableau à transformer
74 * @param string $glue
75 *     Chaine insérée entre les valeurs
76 * @return string|bool
77 *     - False si pas un tableau
78 *     - Chaine concaténée sinon
79**/
80function fabrique_implode_recursif($tableau, $glue='') {
81        if (!is_array($tableau)) {
82                return false;
83        }
84
85        foreach ($tableau as $c =>$valeur) {
86                if (is_array($valeur)) {
87                        $tableau[$c] = fabrique_implode_recursif($valeur, $glue);
88                }
89        }
90
91        return implode($glue, $tableau);
92}
93
94
95/**
96 * Écrit une ouverture de code PHP
97 *
98 * Fait écrire '<?php' sans que ce php soit executé par SPIP !
99 *
100 * @param Champ $p
101 *     Pile au niveau de la balise
102 * @return Champ
103 *     Pile complétée du code à produire
104**/
105function balise_PHP_dist($p) {
106        $p->code = "'<?php echo \'<?php\n\'; ?>'";
107        $p->interdire_scripts = false;
108        return $p;
109}
110
111/**
112 * Convertie une chaîne pour en faire une chaîne de langue
113 *
114 * Permet d'insérer un texte comme valeur d'une clé de langue, lorsqu'on
115 * crée un fichier de langue avec la fabrique.
116 *
117 * Transforme les caractères &# et échappe les apostrophes :
118 * - &#xxx => le bon caractère
119 * - ' => \'
120 *
121 * @example
122 *     '#ENV{prefixe}_description' => '[(#ENV{paquet/description}|chaine_de_langue)]',
123 *
124 * @link http://www.php.net/manual/fr/function.html-entity-decode.php#104617
125 * @param string $texte
126 *     Le texte à écrire dans la chaîne de langue
127 * @return string
128 *     Le texte transformé
129**/
130function chaine_de_langue($texte) {
131        $texte = html_entity_decode($texte, ENT_QUOTES, 'UTF-8');
132        # egalement
133        # http://www.php.net/manual/fr/function.html-entity-decode.php#104617
134
135        return addslashes($texte);
136}
137
138/**
139 * Modifie le nom de la clé de langue pour
140 * utiliser le vrai nom de l'objet
141 *
142 * Remplace 'objets' par le nom de l'objet, et 'objet' par le type d'objet,
143 * mais ne touche pas à '\objets' ou '\objet'.
144 *
145 * @note
146 *     Cette fonction ne sert pas uniquement à définir des clés pour
147 *     les fichiers de chaînes de langue, et pourrait être renommée
148 *
149 * @example
150 *     cle_de_langue('titre_objets') => titre_chats
151 *     cle_de_langue('icone_creer_objet') => icone_creer_chat
152 *     cle_de_langue('prive/\objets/infos/objet.html') => prive/objets/infos/chat.html
153 * @param string $cle
154 *     La clé à transformer
155 * @param array $desc_objet
156 *     Couples d'information sur l'objet en cours, avec les index
157 *     'objet' et 'type' définis
158 * @retrun string
159 *     La clé transformée
160**/
161function cle_de_langue($cle, $desc_objet) {
162        // on permet d'echapper \objets pour trouver 'objets' au bout du compte
163        // sans qu'il soit transforme dans le nom reel de l'objet
164        // cas : 'prive/\objets/infos/objet.html' => 'prive/objets/infos/nom.html'
165        $cle = str_replace("\o", "\1o\\", $cle);
166        $cle =  str_replace(
167                array('objets', 'objet'),
168                array($desc_objet['objet'], $desc_objet['type']), $cle);
169        return str_replace("\1o\\", "o", $cle);
170}
171
172/**
173 * Identique à |cle_de_langue sur toutes les valeurs d'un tableau
174 *
175 * @see cle_de_langue()
176 * @param array $tableau
177 *     Tableau dont on veut transformer les valeurs
178 * @param array $desc_objet
179 *     Couples d'information sur l'objet en cours, avec les index
180 *     'objet' et 'type' définis
181 * @return array
182 *     Tableau avec les valeurs transformées
183**/
184function tab_cle_de_langue($tableau, $desc_objet) {
185        foreach($tableau as $c => $v) {
186                $tableau[$c] = cle_de_langue($v, $desc_objet);
187        }
188        return $tableau;
189}
190
191/**
192 * Cherche s'il existe une chaîne de langue pour les clés de tableaux
193 * et ajoute alors la traduction dans la valeur de ce tableau
194 *
195 * @param array $tableau
196 *     Couples (clé => texte)
197 * @param string $prefixe_cle
198 *     Préfixe ajouté aux clés pour chercher les trads
199 * @param string $sep
200 *     Séparateur entre l'ancienne valeur et la concaténation de traduction
201 * @return array
202 *     Couples (clé => texte complété de la traduction si elle existe)
203**/
204function tab_cle_traduite_ajoute_dans_valeur($tableau, $prefixe_cle="", $sep = "&nbsp;: ") {
205        foreach($tableau as $c => $v) {
206                $trad = _T("fabrique:". $prefixe_cle . $c, array(), array('force' => false));
207                if ($trad) {
208                        $tableau[$c] = $v . $sep . $trad;
209                } else {
210                        $tableau[$c] = $v;
211                }
212        }
213        return $tableau;
214}
215
216/**
217 * Équivalent de wrap() sur les valeurs du tableau
218 *
219 * @param array $tableau
220 *     Tableau cle => texte
221 * @param string $balise
222 *     Balise qui encapsule
223 * @return array $tableau
224 *     Tableau clé => <balise>texte</balise>
225**/
226function tab_wrap($tableau, $balise) {
227        foreach ($tableau as $c => $v) {
228                $tableau[$c] = wrap($v, $balise);
229        }
230        return $tableau;
231}
232
233
234/**
235 * Fabrique un tableau de chaînes de langues
236 * avec des clés d'origines passées dans la fonctions
237 * cle_de_langue, et trie.
238 *
239 * @param array $objet
240 *     Description de l'objet dans la fabrique
241 * @return array
242 *     Couples (clé de langue => Texte)
243**/
244function fabriquer_tableau_chaines($objet) {
245        $chaines = array();
246        if (!is_array($objet)) { return $chaines; }
247        if (!$table = $objet['table'] OR !is_array($objet['chaines'])) { return $chaines; }
248        // les chaines definies pour l'objet
249        foreach ($objet['chaines'] as $cle => $chaine) {
250                $chaines[ cle_de_langue($cle, $objet) ] = $chaine;
251        }
252        // les chaines definies pour chaque champ de l'objet
253        if (is_array($objet['champs'])) {
254                foreach ($objet['champs'] as $info) {
255                        $chaines[ cle_de_langue('label_' . $info['champ'], $objet) ] = $info['nom'];
256                        if ($info['explication']) {
257                                $chaines[ cle_de_langue('explication_' . $info['champ'], $objet) ] = $info['explication'];
258                        }
259                }
260        }
261        // les rôles définis
262        if ($roles = fabrique_description_roles($objet)) {
263                foreach ($roles['roles_trads'] as $cle => $texte) {
264                        $chaines[ $cle ] = $texte;
265                }
266        }
267
268        ksort($chaines);
269        return $chaines;
270}
271
272/**
273 * Retourne la description des rôles pour un objet
274 *
275 * @param array $objet
276 *     Descrption de l'objet
277 * @return array
278 *     Description des rôles. 4 index :
279 *     - roles_colonne : la colonne utilisée, toujours 'role'
280 *     - roles_titre   : couples clé du role, clé de langue du role
281 *     - roles_objets  : tableau objet => liste des clés de roles
282 *     - roles_trads   : couples clé de langue => Texte
283 *     - roles_defaut  : la clé du role par défaut
284 */
285function fabrique_description_roles($objet) {
286        $desc = array();
287        // les rôles définis
288        if (!options_presentes($objet, array('table_liens', 'roles'))
289        OR !($roles = trim($objet['roles']))) {
290                return $desc;
291        }
292        $desc['roles_colonne'] = 'role';
293        $desc['roles_titres'] = array(); # cle => cle_langue
294        $desc['roles_objets'] = array();
295        $desc['roles_trads']  = array(); # cle_langue => Texte
296        $desc['roles_defaut']  = '';
297
298        $roles = explode("\n", $roles);
299        foreach ($roles as $i=>$r) {
300                list($cle, $texte) = explode(',', $r, 2);
301                $cle = trim($cle);
302                if (!$i) $desc['roles_defaut'] = $cle; # la valeur par défaut est la première indiquée
303                $cle_langue = 'role_' . $cle;
304                $desc['roles_titres'][$cle] = $objet['type'] . ':' . $cle_langue;
305                $desc['roles_trads'][$cle_langue] = trim($texte);
306        }
307        $liens = array_map('table_objet', $objet['vue_liens']);
308        foreach ($liens as $l) {
309                $desc['roles_objets'][$l] = array_keys($desc['roles_titres']);
310        }
311        return $desc;
312}
313
314
315/**
316 * Indique si le champ est présent dans l'objet
317 *
318 * Champ, au sens de colonne SQL
319 *
320 * @param array $objet
321 *     Descrption de l'objet
322 * @param string $champ
323 *     Nom du champ SQL à tester
324 * @return string
325 *     Même retour que le filtre |oui :
326 *     - Un espace si le champ SQL exsitera dans l'objet
327 *     - Chaîne vide sinon
328**/
329function champ_present($objet, $champ) {
330        if (is_array($objet['champs'])) {
331                foreach ($objet['champs'] as $info) {
332                        if ($info['champ'] == $champ) {
333                                return " "; // true
334                        }
335                }
336        }
337        // id_rubrique, id_secteur
338        if (isset($objet['rubriques']) AND is_array($objet['rubriques'])) {
339                if (in_array($champ, $objet['rubriques'])) {
340                        return " "; // true
341                }
342        }
343        // lang, langue_choisie, id_trad
344        if (isset($objet['langues']) AND is_array($objet['langues'])) {
345                if (in_array($champ, $objet['langues'])) {
346                        return " "; // true
347                }
348                if ($objet['langues']['lang'] and ($champ == 'langue_choisie')) {
349                        return " "; // true
350                }
351        }
352        // date
353        if ($objet['champ_date']) {
354                if ($champ == $objet['champ_date']) {
355                        return " "; // true
356                }
357        }
358        // statut
359        if ($objet['statut']) {
360                if ($champ == 'statut') {
361                        return " "; // true
362                }
363        }
364
365        return ""; // false
366}
367
368
369/**
370 * Indique si toutes les options sont présentes dans l'objet
371 *
372 * Option au sens de clé de configuration, pas un nom de champ SQL
373 *
374 * @param array $objet
375 *     Descrption de l'objet
376 * @param array $champs
377 *     Liste de nom d'options à tester
378 * @return string
379 *     Même retour que le filtre |oui :
380 *     - Un espace si toutes les options sont présentes dans l'objet
381 *     - Chaîne vide sinon
382**/
383function options_presentes($objet, $champs) {
384        if (!$champs) return false;
385        if (!is_array($champs)) $champs = array($champs);
386        foreach ($champs as $champ) {
387                if (!option_presente($objet, $champ)) {
388                        return ""; // false
389                }
390        }
391        return " "; // true
392
393}
394
395/**
396 * Indique si une option est présente dans l'objet
397 *
398 * Option au sens de clé de configuration, pas un nom de champ SQL
399 *
400 * @param array $objet
401 *     Descrption de l'objet
402 * @param array $champ
403 *     Nom de l'option à tester
404 * @return string
405 *     Même retour que le filtre |oui :
406 *     - Un espace si l'option est présente dans l'objet
407 *     - Chaîne vide sinon
408**/
409function option_presente($objet, $champ) {
410        // a la racine
411        if (isset($objet[$champ]) and $objet[$champ]) {
412                return " "; // true
413        }
414
415        // id_rubrique, vue_rubrique
416        if (isset($objet['rubriques']) AND is_array($objet['rubriques'])) {
417                if (in_array($champ, $objet['rubriques'])) {
418                        return " "; // true
419                }
420        }
421
422        // lang, id_trad
423        if (isset($objet['langues']) AND is_array($objet['langues'])) {
424                if (in_array($champ, $objet['langues'])) {
425                        return " "; // true
426                }
427        }
428       
429        // menu_edition, outils_rapides
430        if (isset($objet['boutons']) AND is_array($objet['boutons'])) {
431                if (in_array($champ, $objet['boutons'])) {
432                        return " "; // true
433                }
434        }
435
436        return ""; // false
437}
438
439
440/**
441 * Indique si une option donnée est presente dans la définition d'un champ
442 * de la fabrique
443 *
444 * @param array $champ
445 *     Description d'un champ SQL d'un objet créé avec la fabrique
446 * @param string $option
447 *     Option testée
448 * @return string
449 *     Même retour que le filtre |oui :
450 *     - Un espace si l'option est présente dans le champ de l'objet
451 *     - Chaîne vide sinon
452 */
453function champ_option_presente($champ, $option) {
454        if (isset($champ[$option]) and $champ[$option]) {
455                return " "; // true
456        }
457
458        // editable, versionne, obligatoire
459        if (isset($champ['caracteristiques']) and is_array($champ['caracteristiques'])) {
460                if (in_array($option, $champ['caracteristiques'])) {
461                        return " "; // true
462                }
463        }
464
465        return false;
466}
467
468/**
469 * Retourne les objets possédant un certain champ SQL
470 *
471 * Cela simplifie des boucles DATA
472 *
473 * @example
474 *     #OBJETS|objets_champ_present{id_rubrique}
475 *
476 *     On peut ne retourner qu'une liste de type de valeur (objet, type, id_objet)
477 *     #OBJETS|objets_champ_present{id_rubrique, objet} // chats,souris
478 *
479 * @param array $objets
480 *     Liste des descriptions d'objets créés avec la fabrique
481 * @param string $champ
482 *     Type de champ sélectionné
483 * @param string $type
484 *     Information de retour désiré :
485 *     - vide pour toute la description de l'objet
486 *     - clé dans la description de l'objet pour obtenir uniquement ces descriptions
487 * @return array
488 *     - tableau de description des objets sélectionnés (si type non défini)
489 *     - tableau les valeurs du type demandé dans les objets sélectionnés (si type défini)
490**/
491function objets_champ_present($objets, $champ, $type='') {
492        return _tableau_option_presente('champ_present', $objets, $champ, $type);
493}
494
495
496/**
497 * Retourne les objets possédant une certaine option
498 *
499 * Option au sens des clés du formulaire de configuration de l'objet
500 *
501 * @example
502 *     #OBJETS|objets_option_presente{vue_rubrique}
503 *     #OBJETS|objets_option_presente{auteurs_liens}
504 *
505 *     On peut ne retourner qu'une liste de type de valeur (objet, type, id_objet)
506 *     #OBJETS|objets_option_presente{auteurs_liens, objet} // chats,souris
507 *
508 * @param array $objets
509 *     Liste des descriptions d'objets créés avec la fabrique
510 * @param string $option
511 *     Type d'option sélectionnée
512 * @param string $type
513 *     Information de retour désiré :
514 *     - vide pour toute la description de l'objet
515 *     - clé dans la description de l'objet pour obtenir uniquement ces descriptions
516 * @return array
517 *     - tableau de description des objets sélectionnés (si type non défini)
518 *     - tableau les valeurs du type demandé dans les objets sélectionnés (si type défini)
519**/
520function objets_option_presente($objets, $option, $type='') {
521        return _tableau_option_presente('option_presente', $objets, $option, $type);
522}
523
524
525/**
526 * Retourne les objets possédant plusieurs options
527 *
528 * Option au sens des clés du formulaire de configuration de l'objet
529 *
530 * @example
531 *     #OBJETS|objets_options_presentes{#LISTE{table_liens,vue_liens}}
532 *
533 *     On peut ne retourner qu'une liste de type de valeur (objet, type, id_objet)
534 *     #OBJETS|objets_options_presentes{#LISTE{table_liens,vue_liens}, objet} // chats,souris
535 *
536 * @param array $objets
537 *     Liste des descriptions d'objets créés avec la fabrique
538 * @param array $options
539 *     Liste de type d'option à sélectionner
540 * @param string $type
541 *     Information de retour désiré :
542 *     - vide pour toute la description de l'objet
543 *     - clé dans la description de l'objet pour obtenir uniquement ces descriptions
544 * @return array
545 *     - tableau de description des objets sélectionnés (si type non défini)
546 *     - tableau les valeurs du type demandé dans les objets sélectionnés (si type défini)
547**/
548function objets_options_presentes($objets, $options, $type='') {
549        return _tableau_options_presentes('option_presente', $objets, $options, $type);
550}
551
552/**
553 * Retourne des champs en fonction d'une option trouvée
554 *
555 * @example
556 *     #CHAMPS|champs_option_presente{editable}
557 *     #CHAMPS|champs_option_presente{versionne}
558 *
559 * @param array $champs
560 *     Liste des descriptions de champs d'un objet créé avec la fabrique
561 * @param string $option
562 *     Type d'option sélectionnée
563 * @param string $type
564 *     Information de retour désiré :
565 *     - vide pour toute la description du champ
566 *     - clé dans la description du champ pour obtenir uniquement ces descriptions
567 * @return array
568 *     - tableau de description des champs sélectionnés (si type non défini)
569 *     - tableau les valeurs du type demandé dans les champs sélectionnés (si type défini)
570**/
571function champs_option_presente($champs, $option, $type='') {
572        return _tableau_option_presente('champ_option_presente', $champs, $option, $type);
573}
574
575/**
576 * Retourne des champs en fonction des options trouvées
577 *
578 * @example
579 *     #CHAMPS|champs_options_presentes{#LISTE{obligatoire,saisie}}
580 *
581 * @param array $champs
582 *     Liste des descriptions de champs d'un objet créé avec la fabrique
583 * @param array $options
584 *     Liste de type d'options à sélectionner
585 * @param string $type
586 *     Information de retour désiré :
587 *     - vide pour toute la description du champ
588 *     - clé dans la description du champ pour obtenir uniquement ces descriptions
589 * @return array
590 *     - tableau de description des champs sélectionnés (si type non défini)
591 *     - tableau les valeurs du type demandé dans les champs sélectionnés (si type défini)
592**/
593function champs_options_presentes($champs, $options, $type='') {
594        return _tableau_options_presentes('champ_option_presente', $champs, $options, $type);
595}
596
597
598/**
599 * Fonction générique pour retourner une liste de choses dans un tableau
600 *
601 * @param string $func
602 *     Nom de la fonction à appeler, tel que
603 *     - champ_option_presente
604 *     - option_presente
605 *     - ...
606 * @param array $tableau
607 *     Tableau de descriptions (descriptions d'objet ou descriptions de champ d'objet)
608 * @param string $option
609 *     Nom de l'option dont on teste la présence
610 * @param string $type
611 *     Information de retour désiré :
612 *     - vide pour toute la description
613 *     - clé dans la description pour obtenir uniquement ces descriptions
614 * @return array
615 *     Liste des descriptions correspondant à l'option demandée
616 */
617function _tableau_option_presente($func, $tableau, $option, $type='') {
618        $o = array();
619
620        if (!is_array($tableau) OR !$func) {
621                return $o;
622        }
623        // tableau est un tableau complexe de donnee
624        foreach ($tableau as $objet) {
625                // on cherche la donnee 'option' dans le tableau
626                // en utilisant une fonction specifique de recherche (option_presente, champ_present, ...)
627                if ($func($objet, $option)) {
628                        // si on a trouve notre option :
629                        // type permet de recuperer une cle specifique dans la liste des cles parcourues.
630                        // sinon, retourne tout le sous tableau.
631                        if ($type and isset($objet[$type])) {
632                                $o[] = $objet[$type];
633                        } elseif (!$type) {
634                                $o[] = $objet;
635                        }
636                }
637        }
638        return $o;
639}
640
641/**
642 * Fonction générique pour retourner une liste de choses multiples dans un tableau
643 *
644 * @param string $func
645 *     Nom de la fonction à appeler, tel que
646 *     - champ_option_presente
647 *     - option_presente
648 *     - ...
649 * @param array $tableau
650 *     Tableau de descriptions (descriptions d'objet ou descriptions de champ d'objet)
651 * @param array $options
652 *     Nom des l'options dont on teste leur présence
653 * @param string $type
654 *     Information de retour désiré :
655 *     - vide pour toute la description
656 *     - clé dans la description pour obtenir uniquement ces descriptions
657 * @return array
658 *     Liste des descriptions correspondant aux options demandées
659 */
660function _tableau_options_presentes($func, $tableau, $options, $type='') {
661        if (!$options) return array();
662
663        if (!is_array($options)) {
664                $options = array($options);
665        }
666
667        $first = false;
668        foreach ($options as $option) {
669                $r = _tableau_option_presente($func, $tableau, $option, $type);
670                if (!$first) {
671                        $res = $r;
672                        $first = true;
673                } else {
674                        #$res = array_intersect($res, $r);
675                        // array_intersect() ne prend pas en compte les sous tableaux
676                        foreach ($res as $i => $v) {
677                                if (false === array_search($v, $r)) {
678                                        unset($res[$i]);
679                                }
680                        }
681                        $res = array_values($res);
682                }
683        }
684
685        return $res;
686}
687
688
689/**
690 * Retourne une ecriture de criteres
691 * {id_parent?}{id_documentation?}
692 * avec tous les champs id_x declarés dans l'interface
693 * dans la liste des champs.
694 *
695 * Cela ne concerne pas les champs speciaux (id_rubrique, id_secteur, id_trad)
696 * qui ne seront pas inclus.
697 *
698 * @param array $objet
699 *     Description de l'objet dans la fabrique
700 * @return string
701 *     L'écriture des critères de boucle
702**/
703function criteres_champs_id($objet) {
704        $ids = array();
705        if (is_array($objet['champs'])) {
706                foreach ($objet['champs'] as $info) {
707                        if (substr($info['champ'], 0, 3) == 'id_') {
708                                $ids[] = $info['champ'];
709                        }
710                }
711        }
712        if (!$ids) {
713                return "";
714        }
715        return "{" . implode("?}{", $ids) . "?}";
716}
717
718/**
719 * Retourne un tableau de toutes les tables SQL
720 * pour tous les objets.
721 *
722 * @param array $objets
723 *     Liste des descriptions d'objets créés avec la fabrique
724 * @param string $quoi
725 *     Choix du retour désiré :
726 *     - 'tout'   => toutes les tables (par défaut)
727 *     - 'objets' => les tables d'objet (spip_xx, spip_yy)
728 *     - 'liens'  => les tables de liens (spip_xx_liens, spip_yy_liens)
729 * @return array
730 *     Liste des tables
731**/
732function fabrique_lister_tables($objets, $quoi='tout') {
733        static $tables = array();
734
735        if (!$objets) return array();
736
737        $hash = md5(serialize($objets));
738       
739        if (!isset($tables[$hash])) {
740                $tables[$hash] = array(
741                        'tout' => array(),
742                        'objets' => array(),
743                        'liens' => array(),
744                );
745                foreach ($objets as $o) {
746                        // tables principales
747                        if (isset($o['table']) and $o['table']) {
748                                $tables[$hash]['objets'][] = $o['table'];
749                                $tables[$hash]['tout'][] = $o['table'];
750                                // tables de liens
751                                if ($o['table_liens']) {
752                                        $tables[$hash]['liens'][] = $o['nom_table_liens'];
753                                        $tables[$hash]['tout'][]  = $o['nom_table_liens'];
754                                }
755                        }
756                }
757        }
758       
759        return $tables[$hash][$quoi];
760}
761
762
763/**
764 * Indique si un des objets a besoin du pipeline demandé
765 *
766 * @param array $objets
767 *     Liste des descriptions d'objets créés avec la fabrique
768 * @param string $pipeline
769 *     Nom du pipeline
770 * @return array
771 *     Liste des objets (descriptions) utilisant le pipeline
772 */
773function fabrique_necessite_pipeline($objets, $pipeline) {
774
775        if (!$objets) return false;
776
777        switch ($pipeline) {
778                case "autoriser":
779                case "declarer_tables_objets_sql":
780                case "declarer_tables_interfaces":
781                        return (bool)fabrique_lister_tables($objets, 'objets');
782                        break;
783
784                case "declarer_tables_auxiliaires":
785                        return (bool)fabrique_lister_tables($objets, 'liens');
786                        break;
787
788                case "affiche_enfants":
789                        if (objets_option_presente($objets, 'vue_rubrique')) {
790                                return true;
791                        }
792                        break;
793
794                case "affiche_milieu":
795                        if (objets_option_presente($objets, 'auteurs_liens')
796                        OR  objets_options_presentes($objets, array('table_liens', 'vue_liens'))) {
797                                return true;
798                        }
799                        break;
800
801                case "affiche_auteurs_interventions":
802                        if (objets_option_presente($objets, 'vue_auteurs_liens')) {
803                                return true;
804                        }
805                        break;
806
807                case "afficher_contenu_objet":
808                        return false;
809                        break;
810
811                case "optimiser_base_disparus":
812                        # nettoie depuis spip_{objet}_liens
813                        # mais aussi les liaisions vers spip_{objet} (uniquement si une table de liens existe)
814                        return (bool)fabrique_lister_tables($objets, 'liens');
815                        #return (bool)fabrique_lister_tables($objets, 'objets');
816                        break;
817        }
818        return false;
819}
820
821
822/**
823 * Crée le code PHP de création d'un tableau
824 *
825 * Fonction un peu équivalente à var_export()
826 *
827 * @param array $tableau
828 *     Le tableau dont on veut obtenir le code de création array( ... )
829 * @param bool $quote
830 *     Appliquer sql_quote() sur chaque valeur (dans le code retourne)
831 * @param string $defaut
832 *     Si $tableau est vide ou n'est pas une chaîne, la fonction retourne cette valeur
833 * @return string
834 *     - Le code de création du tableau, avec éventuellement le code pour appliquer sql_quote.
835 *     - $defaut si le tableau est vide
836**/
837function ecrire_tableau($tableau, $quote = false, $defaut = "array()") {
838        // pas de tableau ?
839        if (!is_array($tableau) OR !count($tableau)) {
840                return $defaut;
841        }
842
843        $res = "array('" . implode("', '", array_map('addslashes', $tableau)) . "')";
844
845        if ($quote) {
846                $res = "array_map('sql_quote', $res)";
847        }
848        return $res;
849}
850
851/**
852 * Crée le code PHP de création d'un tableau sauf s'il est vide
853 *
854 * Identique à ecrire_tableau() mais ne retourne rien si le tableau est vide
855 * @see ecrire_tableau()
856 *
857 * @param array $tableau
858 *     Le tableau dont on veut obtenir le code de création array( ... )
859 * @param bool $quote
860 *     Appliquer sql_quote() sur chaque valeur (dans le code retourne)
861 * @return string
862 *     - Le code de création du tableau, avec éventuellement le code pour appliquer sql_quote.
863 *     - Chaîne vide si le tableau est vide
864**/
865function ecrire_tableau_sinon_rien($tableau, $quote = false) {
866        return ecrire_tableau($tableau, $quote, "");
867}
868
869/**
870 * Ajoute autant des espaces à la fin d'une chaîne jusqu'à la taille indiquée
871 *
872 * Fonction un peu equivalente à str_pad() mais avec une valeur par défaut
873 * définie par la constante _FABRIQUE_ESPACER
874 *
875 * @param string $texte
876 *     Texte à compléter
877 * @param int $taille
878 *     Taille spécifique, utilisée à la place de la constante si renseignée
879 * @return
880 *     Texte complété des espaces de fin
881 */
882function espacer($texte, $taille = 0) {
883        if (!$taille) $taille = _FABRIQUE_ESPACER;
884        return str_pad($texte, $taille);
885}
886
887
888/**
889 * Tabule à gauche chaque ligne du nombre de tabulations indiquées
890 * + on enleve les espaces sur les lignes vides
891 *
892 * @param string $texte
893 *     Un texte, qui peut avoir plusieurs lignes
894 * @param int $nb_tabulations
895 *     Nombre de tabulations à appliquer à gauche de chaque ligne
896 * @return string
897 *     Texte indenté du nombre de tabulations indiqué
898 */
899function fabrique_tabulations($texte, $nb_tabulations) {
900        $tab = "";
901        if ($nb_tabulations) {
902                $tab = str_pad("\t", $nb_tabulations);
903        }
904        $texte = explode("\n", $texte);
905        foreach ($texte as $c => $ligne) {
906                $l = ltrim(ltrim($ligne), "\t");
907                if (!$l) {
908                        $texte[$c] = "";
909                } else {
910                        $texte[$c] = $tab . $ligne;
911                }
912        }
913        return implode("\n", $texte);
914}
915
916
917
918
919/**
920 * Passer en majuscule en utilisant mb de préférence
921 * s'il est disponible.
922 *
923 * @param string $str
924 *     La chaine à passer en majuscule
925 * @return string
926 *     La chaine en majuscule
927**/
928function fabrique_mb_strtoupper($str) {
929        if (function_exists('mb_strtoupper')) {
930                return mb_strtoupper($str);
931        } else {
932                return strtoupper($str);
933        }
934}
935
936/**
937 * Passer en minuscule en utilisant mb de préférence
938 * s'il est disponible.
939 *
940 * @param string $str
941 *              La chaine à passer en minuscule
942 * @return string
943 *              La chaine en minuscule
944**/
945function fabrique_mb_strtolower($str) {
946        if (function_exists('mb_strtolower')) {
947                return mb_strtolower($str);
948        } else {
949                return strtolower($str);
950        }
951}
952
953
954/**
955 * Crée une balise HTML <img> à partir d'un fichier,
956 * réactualisée à chaque calcul, selon une réduction donnée.
957 *
958 * Cela évite un |array_shift qui ne passe pas en PHP 5.4
959 *
960 * Attention à bien rafraîchir l'image réduite lorsqu'on change de logo.
961 *
962 * @example
963 *     #URL_IMAGE|fabrique_miniature_image{128}
964 *
965 *     Applique l'équivalent de :
966 *     #URL_IMAGE|image_reduire{128}|extraire_attribut{src}
967 *         |explode{?}|array_shift|timestamp|balise_img
968 *
969 * @param string $fichier
970 *     Chemin du fichier
971 * @param int $taille
972 *     Taille de réduction de l'image
973 * @return string
974 *     Balise HTML IMG de l'image réduite et à jour
975 */
976function filtre_fabrique_miniature_image($fichier, $taille=256) {
977        $im = filtrer('image_reduire', $fichier, $taille);
978        $im = extraire_attribut($im, 'src');
979        $im = explode('?', $im);
980        $im = array_shift($im);
981        $im = timestamp($im);
982        $im = filtrer('balise_img', $im);
983        return $im;
984}
985
986
987
988/**
989 * Retourne un tableau table_sql=>Nom des objets de SPIP
990 * complété des objets declares dans la fabrique ainsi
991 * que de tables indiquees même si elles ne font pas parties
992 * de declarations connues.
993 *
994 * @param array $objets_fabrique
995 *              Déclaration d'objets de la fabrique
996 * @param array $inclus
997 *              Liste de tables SQL que l'on veut forcement presentes
998 *              meme si l'objet n'est pas declare
999 * @param array $exclus
1000 *              Liste de tables SQL que l'on veut forcement exclues
1001 *              meme si l'objet n'est pas declare
1002 * @return array
1003 *              Tableau table_sql => Nom
1004**/
1005function filtre_fabrique_lister_objets_editoriaux($objets_fabrique, $inclus=array(), $exclus=array()) {
1006
1007        // les objets existants
1008        $objets = lister_tables_objets_sql();
1009        foreach ($objets as $sql => $o) {
1010                if ($o['editable']) {
1011                        $liste[$sql] = _T($o['texte_objets']);
1012                }
1013        }
1014        unset($objets);
1015
1016        // les objets de la fabrique
1017        foreach ($objets_fabrique as $o) {
1018                if (isset($o['table']) and !isset($liste[$o['table']])) {
1019                        $liste[ $o['table'] ] = $o['nom'];
1020                }
1021        }
1022
1023        // des objets qui n'existent pas mais qui sont actuellement coches dans la saisie
1024        foreach ($inclus as $sql) {
1025                if (!isset($liste[$sql])) {
1026                        $liste[$sql] = $sql; // on ne connait pas le nom
1027                }
1028        }
1029
1030        // tables forcement exclues
1031        foreach ($exclus as $sql) {
1032                unset($liste[$sql]);
1033        }
1034        // enlever un eventuel element vide
1035        unset($liste['']);
1036
1037        asort($liste);
1038
1039        return $liste;
1040}
1041
1042
1043/**
1044 * Retourne le code pour tester un type d'autorisation
1045 *
1046 * @param string $type
1047 *              Quelle type d'autorisation est voulue
1048 * @return string
1049 *              Code de test de l'autorisation
1050**/
1051function fabrique_code_autorisation($type) {
1052        switch($type) {
1053
1054                case "jamais":
1055                        return "false";
1056                        break;
1057
1058                case "toujours":
1059                        return "true";
1060                        break;
1061
1062                case "redacteur":
1063                        return "in_array(\$qui['statut'], array('0minirezo', '1comite'))";
1064                        break;
1065
1066                case "administrateur_restreint":
1067                        return "\$qui['statut'] == '0minirezo'";
1068                        break;
1069
1070                case "administrateur":
1071                        return "\$qui['statut'] == '0minirezo' AND !\$qui['restreint']";
1072                        break;
1073
1074                case "webmestre":
1075                        return "autoriser('webmestre', '', '', \$qui)";
1076                        break;
1077
1078        }
1079
1080        return "";
1081}
1082
1083/**
1084 * Retourne la valeur de type d'autorisation
1085 * qui s'applique par defaut pour une autorisation donnee
1086 *
1087 * @param string $autorisation
1088 *              Nom de l'autorisation (objet et objets remplacent le veritable type et nom d'objet)
1089 * @return string
1090 *              Type d'autorisation par defaut (jamais, toujours, redacteur, ...)
1091**/
1092function fabrique_autorisation_defaut($autorisation) {
1093        switch($autorisation) {
1094                case 'objet_voir':
1095                        return "toujours";
1096                        break;
1097
1098                case 'objet_creer':
1099                case 'objet_modifier':
1100                        return "redacteur";
1101                        break;
1102
1103                case 'objet_supprimer':
1104                case 'associerobjet':
1105                        return "administrateur";
1106                        break;
1107        }
1108}
1109
1110/**
1111 * Retourne le code d'autorisation indique
1112 * sinon celui par defaut pour une fonction d'autorisation
1113 *
1114 * @param array $autorisations
1115 *              Les autorisations renseignees par l'interface pour un objet
1116 * @param string $autorisation
1117 *              Le nom de l'autorisation souhaitee
1118 * @return string
1119 *              Code de l'autorisation
1120**/
1121function fabrique_code_autorisation_defaut($autorisations, $autorisation) {
1122        if (!$autorisation) return "";
1123
1124        // trouver le type d'autorisation souhaitee, soit indiquee, soit par defaut
1125        if (!isset($autorisations[$autorisation]) OR !$type = $autorisations[$autorisation]) {
1126                $type = fabrique_autorisation_defaut($autorisation);
1127        }
1128
1129        // retourner le code PHP correspondant
1130        return fabrique_code_autorisation($type);
1131}
1132
1133/**
1134 * Retourne le type pour le nom d'une fonction d'autorisation
1135 * 'article' => 'article'
1136 * 'truc_muche' => 'trucmuche'
1137 *
1138 * @param string $type
1139 *              Type ou objet
1140 * @return string
1141 *              Type pour le nom d'autorisation
1142**/
1143function fabrique_type_autorisation($type) {
1144        return str_replace('_', '', $type);
1145}
1146
1147?>
Note: See TracBrowser for help on using the repository browser.