source: spip-zone/_plugins_/isocode/trunk/isocode_fonctions.php @ 100330

Last change on this file since 100330 was 100330, checked in by eric@…, 5 years ago

PSR SPIP.
Les fonctions de lectures par type de source ont été remplacées par une seule fonction générique.

  • Property svn:eol-style set to native
File size: 11.5 KB
Line 
1<?php
2/**
3 * Ce fichier contient l'ensemble des fonctions implémentant l'API du plugin.
4 *
5 * @package SPIP\ISOCODE\API
6 */
7if (!defined('_ECRIRE_INC_VERSION')) {
8        return;
9}
10
11
12/**
13 * Charge en base de données une liste de tables de codes ISO donnée.
14 * Si la liste est vide, la fonction charge toutes les tables disponibles.
15 *
16 * @api
17 * @filtre
18 *
19 * @uses isocode_trouver_service()
20 * @uses isocode_decharger_tables()
21 *
22 * @param array $tables
23 *      Liste des tables à charger. Si le tableau est vide l'ensemble des tables
24 *      seront chargées.
25 *      Les tables doivent être libellées sans le préfixe `spip_`.
26 *
27 * @return array
28 *      Tableau résultat de l'action de vidage:
29 *      - index 0 : `true` si le vidage a réussi, `false` sinon.
30 *      - index 1 : liste des tables en erreur ou tableau vide sinon.
31 *        - index 2 : liste des tables inchangées ou tableau vide sinon.
32 */
33function isocode_charger_tables($tables = array()) {
34
35        $retour = array(true, array(), array());
36
37        // Suivant le tableau fourni en argument, on détermine la liste exacte des tables à charger.
38        // Le cas où le service existe mais que la liste de tables associées est vide est traité dans
39        // la boucle des services ci-après.
40        if (!$tables) {
41                // Le tableau est vide : il faut charger toutes les tables de tous les services supportés.
42                $tables = isocode_lister_tables();
43        } elseif (is_string($tables)) {
44                // L'argument n'est pas un tableau mais une chaine, on considère que l'appelant a demandé
45                // le chargement d'une table identifiée par cette chaine.
46                $tables = array($tables);
47        } elseif (!is_array($tables)) {
48                $tables = array();
49        }
50
51        // On charge chacune des tables spécifiées en identifiant au préalable le service concerné.
52        // -- Pour éviter d'avoir une mise à jour bancale, il faudrait inclure les requêtes SQL dans
53        // une transaction ce qui n'est pas possible avec spip aujourd'hui.
54        // De fait, on ne peut pas assurer que si une erreur se produit le résultat soit cohérent et
55        // on renvoie juste l'erreur --
56        if ($tables) {
57                include_spip('inc/config');
58                foreach ($tables as $_table) {
59                        $erreur_table = false;
60                        $sha_identique = false;
61
62                        // On détermine le service qui supporte le chargement de la table
63                        $service = isocode_trouver_service($_table);
64                        if ($service) {
65                                // Détermination de la fonction de lecture de la table et lecture des données contenues
66                                // soit dans un fichier soit dans une page web.
67                                // Si la table est déjà chargée et que le fichier ou la page source n'a pas changé, la fonction de
68                                // lecture ne renvoie aucun élément pour éviter des traitements inutiles. Il faut donc distinguer
69                                // ce cas d'une erreur de lecture.
70                                include_spip("services/${service}/${service}_api");
71                                $lire_table = charger_fonction('isocode_read', 'inc');
72                                list($records, $sha) = $lire_table($service, $_table);
73                                if ($records) {
74                                        // Suppression des éléments éventuels déjà chargés. On ne gère pas d'erreur
75                                        // sur ce traitement car elle sera forcément détectée sur l'insert qui suit.
76                                        isocode_decharger_tables($_table);
77
78                                        // Insertion dans la base de données des éléments extraits
79                                        $sql_ok = sql_insertq_multi("spip_${_table}", $records);
80                                        if ($sql_ok !== false) {
81                                                // On stocke les informations de chargement de la table dans une meta.
82                                                $meta = array(
83                                                        'service' => $service,
84                                                        'sha'     => $sha,
85                                                        'nbr'     => count($records),
86                                                        'maj'     => date('Y-m-d H:i:s')
87                                                );
88                                                ecrire_config("isocode/tables/${_table}", $meta);
89                                        } else {
90                                                $erreur_table = true;
91                                        }
92                                } else {
93                                        // Si le sha n'a pas changé la fonction de lecture renvoie aucun enregistrement mais ce n'est pas
94                                        // une erreur à proprement parlé.
95                                        $erreur_table = true;
96                                        if (isocode_comparer_sha($sha, $_table)) {
97                                                $sha_identique = true;
98                                        }
99                                }
100                        } else {
101                                $erreur_table = true;
102                        }
103
104                        if ($erreur_table) {
105                                $retour[0] = false;
106                                if ($sha_identique) {
107                                        $retour[2][] = $_table;
108                                } else {
109                                        $retour[1][] = $_table;
110                                }
111                        }
112                }
113        }
114
115        return $retour;
116}
117
118
119/**
120 * Supprime en base de données, le contenu des tables de codes ISO choisies.
121 * Si la liste des tables est vide la fonction considère que toutes les tables doivent être vidées.
122 * La meta concernant les informations de chargement de chaque table est aussi effacée.
123 *
124 * @api
125 * @filtre
126 *
127 * @param array $tables
128 *        Liste des noms de table sans le préfixe `spip_`.
129 *
130 * @return array
131 *         Tableau résultat de l'action de vidage:
132 *         - index 0 : `true` si le vidage a réussi, `false` sinon.
133 *         - index 1 : liste des tables en erreur ou tableau vide sinon.
134 */
135function isocode_decharger_tables($tables = array()) {
136
137        $retour = array(true, array());
138
139        // Suivant le tableau fourni en argument, on détermine la liste exacte des tables à charger.
140        // Le cas où le service existe mais que la liste de tables associées est vide est traité dans
141        // la boucle des services ci-après.
142        if (!$tables) {
143                // Le tableau est vide : il faut charger toutes les tables de tous les services supportés.
144                $tables = isocode_lister_tables();
145        } elseif (is_string($tables)) {
146                // L'argument n'est pas un tableau mais une chaine, on considère que l'appelant a demandé
147                // le chargement d'une table identifiée par cette chaine.
148                $tables = array($tables);
149        } elseif (!is_array($tables)) {
150                $tables = array();
151        }
152
153        // On boucle sur la liste des tables et on vide chaque table référencée.
154        if ($tables) {
155                include_spip('inc/config');
156                foreach ($tables as $_table) {
157                        $sql_ok = sql_delete("spip_${_table}");
158                        if ($sql_ok !== false) {
159                                // Supprimer la meta propre à la table.
160                                effacer_config("isocode/tables/${_table}");
161                        } else {
162                                $retour[0] = false;
163                                $retour[1][] = $_table;
164                        }
165                }
166        }
167
168        return $retour;
169}
170
171
172/**
173 * Détermine le service associé au chargement de la table de codes ISO choisie.
174 * Si la table est vide ou invalide, la fonction renvoie une chaine vide.
175 *
176 * @api
177 *
178 * @param $table
179 *        Nom d'une table de codes ISO sans le préfixe `spip_`.
180 *
181 * @return string
182 *        Nom du service permettant le chargement de la table ou chaine vide si aucun service n'est trouvé.
183 */
184function isocode_trouver_service($table) {
185
186        static $services = array();
187        static $tables = array();
188        $service = '';
189
190        if (is_string($table) and $table) {
191                if (!$services) {
192                        $services = isocode_lister_services();
193                }
194
195                foreach ($services as $_service) {
196                        if (!isset($tables[$_service])) {
197                                include_spip("services/${_service}/${_service}_api");
198                                $tables[$_service] = array_keys($GLOBALS['isocode'][$_service]['tables']);
199                        }
200                        if (in_array(strtolower($table), $tables[$_service])) {
201                                $service = $_service;
202                                break;
203                        }
204                }
205        }
206
207        return $service;
208}
209
210
211/**
212 * Retourne la liste des services disponibles pour le chargement des tables de codes ISO.
213 * La fonction lit les sous-répertoires du répertoire `services/` du plugin.
214 *
215 * @api
216 *
217 * @return array
218 *        La liste des services disponibles ou tableau vide aucun service n'est détecté.
219 */
220function isocode_lister_services() {
221
222        $services = array();
223
224        if ($dossiers = glob(_DIR_PLUGIN_ISOCODE . '/services/*', GLOB_ONLYDIR)) {
225                foreach ($dossiers as $_dossier) {
226                        $services[] = strtolower(basename($_dossier));
227                }
228        }
229
230        return $services;
231}
232
233
234/**
235 * Vérifie si le service demandé est fait bien partie de la liste des services disponibles.
236 *
237 * @api
238 *
239 * @param $service
240 *        Nom du service à vérifier.
241 *
242 * @return bool
243 *      `true` si le service est disponible, `false` sinon.
244 */
245function isocode_service_disponible($service) {
246
247        $disponible = false;
248        if ($service and in_array(strtolower($service), isocode_lister_services())) {
249                $disponible = true;
250        }
251
252        return $disponible;
253}
254
255
256/**
257 * Retourne la liste de toutes les tables gérées par le plugin ou de celles associées à un ou plusieurs
258 * services donnés.
259 *
260 * @param array $services
261 *        Liste des services pour lesquels la liste des tables associées est demandée.
262 *        Si la liste est vide la fonction renvoie les tables de tous les services dsponibles.
263 *
264 * @return array
265 *        Liste des tables de codes ISO sans le préfixe `spip_`.
266 */
267function isocode_lister_tables($services = array()) {
268
269        $tables = array();
270
271        // Si le tableau des services est vide c'est que l'on veut toutes les tables de tous
272        // les services disponibles.
273        // On accepte tous les cas où l'argument est vide sans être un tableau.
274        if (!$services) {
275                $services = isocode_lister_services();
276        }
277
278        // Si l'argument est non vide et est une chaine on considère que c'est un service et on le
279        // transforme en un tableau à un élément.
280        // Sinon c'est une erreur.
281        if (!is_array($services)) {
282                $services = is_string($services) ? array($services) : array();
283        }
284
285        // On collecte pour chaque service, la liste des tables qu'il supporte.
286        foreach ($services as $_service) {
287                if (isocode_service_disponible($_service)) {
288                        include_spip("services/${_service}/${_service}_api");
289                        $tables = array_merge($tables, array_keys($GLOBALS['isocode'][$_service]['tables']));
290                }
291        }
292
293        return $tables;
294}
295
296
297/**
298 * Informe sur la liste des tables déjà chagées en base de données.
299 * Les informations de la meta de chaque table sont complétées et renvoyées.
300 *
301 * @api
302 *
303 * @return array
304 *        Liste des tables de codes ISO sans le préfixe `spip_` et leurs informations de chargement.
305 */
306function isocode_informer_tables_chargees() {
307
308        // On initialise la liste des tables en lisant la meta idoine.
309        include_spip('inc/config');
310        $tables = lire_config('isocode/tables', array());
311
312        // On complète chaque bloc d'informations par le nom de la table et son libéllé.
313        if ($tables) {
314                foreach ($tables as $_table => $_informations) {
315                        $tables[$_table]['nom'] = $_table;
316                        $tables[$_table]['libelle'] = _T("isocode:label_table_${_table}");
317                }
318        }
319
320        return $tables;
321}
322
323
324/**
325 * Indique si une table de codes ISO est déjà chargée ou pas en base de données.
326 * La fonction scrute la table `spip_${table}` et non la meta propre à la table.
327 *
328 * @api
329 * @filtre
330 *
331 * @param string $table
332 *        Nom de la table sans le préfixe `spip_`.
333 * @param array  $meta_table
334 *        Meta propre à la table, créée lors du chargement de celle-ci et retournée si la table
335 *        est déjà chargée.
336 *
337 * @return bool
338 *        `true` si la table est chargée, `false` sinon.
339 */
340function isocode_table_chargee($table, &$meta_table) {
341        $meta_table = array();
342        $table_chargee = false;
343
344        $retour = sql_countsel("spip_${table}");
345        if ($retour) {
346                // Récupérer la meta propre au règne afin de la retourner.
347                include_spip('inc/config');
348                $meta_table = lire_config("isocode/tables/${table}");
349                $table_chargee = true;
350        }
351
352        return $table_chargee;
353}
354
355
356/**
357 * Compare le sha passé en argument pour la table concernée avec le sha stocké dans la meta
358 * pour cette même table.
359 *
360 * @api
361 *
362 * @param string $sha
363 *        Sha à comparer à celui de la table.
364 * @param string $table
365 *        Nom de la table de code ISO (sans préfixe `spip_`) dont il faut comparer le sha
366 *        stoké dans sa meta de chargement.
367 *
368 * @return bool
369 *      `true` si le sha passé en argument est identique au sha stocké pour la table choisie, `false` sinon.
370 */
371function isocode_comparer_sha($sha, $table) {
372
373        $sha_identique = false;
374
375        // On récupère le sha de la table dans les metas si il existe (ie. la table a été chargée)
376        include_spip('inc/config');
377        $sha_stocke = lire_config("isocode/tables/${table}/sha", false);
378
379        if ($sha_stocke and ($sha == $sha_stocke)) {
380                $sha_identique = true;
381        }
382
383        return $sha_identique;
384}
Note: See TracBrowser for help on using the repository browser.