Projet

Général

Profil

Paste
Statistiques
| Branche: | Révision:

ryxeo-glpi-git / inc / cron.class.php @ b67d8923

Historique | Voir | Annoter | Télécharger (10,3 ko)

1
<?php
2
/*
3
 * @version $Id: cron.class.php 7763 2009-01-06 18:44:50Z moyo $
4
 -------------------------------------------------------------------------
5
 GLPI - Gestionnaire Libre de Parc Informatique
6
 Copyright (C) 2003-2009 by the INDEPNET Development Team.
7

8
 http://indepnet.net/   http://glpi-project.org
9
 -------------------------------------------------------------------------
10

11
 LICENSE
12

13
 This file is part of GLPI.
14

15
 GLPI is free software; you can redistribute it and/or modify
16
 it under the terms of the GNU General Public License as published by
17
 the Free Software Foundation; either version 2 of the License, or
18
 (at your option) any later version.
19

20
 GLPI is distributed in the hope that it will be useful,
21
 but WITHOUT ANY WARRANTY; without even the implied warranty of
22
 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
23
 GNU General Public License for more details.
24

25
 You should have received a copy of the GNU General Public License
26
 along with GLPI; if not, write to the Free Software
27
 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
28
 --------------------------------------------------------------------------
29
 */
30

    
31
// ----------------------------------------------------------------------
32
// Original Author of file: Adaptation du fichier cron.php de SPIP Merci à leurs auteurs
33
// Purpose of file: cron class
34
// ----------------------------------------------------------------------
35
/***************************************************************************\
36
 *  SPIP, Systeme de publication pour l'internet                           *
37
 *                                                                         *
38
 *  Copyright (c) 2001-2006                                                *
39
 *  Arnaud Martin, Antoine Pitrou, Philippe Riviere, Emmanuel Saint-James  *
40
 *                                                                         *
41
 *  Ce programme est un logiciel libre distribue sous licence GNU/GPL.     *
42
 *  Pour plus de details voir le fichier COPYING.txt                       *
43
 \***************************************************************************/
44

    
45

    
46
// --------------------------
47
// Gestion des taches de fond
48
// --------------------------
49

    
50
// Deux difficultes:
51
// - la plupart des hebergeurs ne fournissent pas le Cron d'Unix
52
// - les scripts usuels standard sont limites a 30 secondes
53

    
54
// Solution:
55
// les scripts usuels les plus brefs, en plus de livrer la page demandee,
56
// s'achevent  par un appel a la fonction cron.
57
// Celle-ci prend dans la liste des taches a effectuer la plus prioritaire.
58
// Une seule tache est executee pour eviter la guillotine des 30 secondes.
59
// Une fonction executant une tache doit retourner un nombre:
60
// - nul, si la tache n'a pas a etre effecutee -> ex il n'y a pas d'échéance de  contrat à notifier
61
// - positif, si la tache a ete effectuee
62
// - negatif, si la tache doit etre poursuivie ou recommencee
63
// Elle recoit en argument la date de la derniere execution de la tache.
64

    
65
// On peut appeler cron avec d'autres taches (pour etendre GLPI)
66
// specifiee par des fonctions respectant le protocole ci-dessus
67
// On peut modifier la frequence de chaque tache et leur ordre d'analyse
68
// en modifiant les variables ci-dessous.
69

    
70
//----------
71

    
72
// Les taches sont dans un array ('nom de la tache' => periodicite)
73
// Cette fonction execute la tache la plus urgente (celle dont la date
74
// de derniere execution + la periodicite est minimale) sous reserve que
75
// le serveur MySQL soit actif.
76
// La date de la derniere intervention est donnee par un fichier homonyme,
77
// de suffixe ".lock", modifie a chaque intervention et des le debut
78
// de celle-ci afin qu'un processus concurrent ne la demarre pas aussi.
79
// Les taches les plus longues sont tronconnees, ce qui impose d'antidater
80
// le fichier de verrouillage (avec la valeur absolue du code de retour).
81
// La fonction executant la tache est un homonyme de prefixe "cron_"
82
// Le fichier homonyme de prefixe "inc_"
83
// est automatiquement charge si besoin, et est supposee la definir si ce
84
// n'est fait ici.
85

    
86
// touch : verifie si un fichier existe et n'est pas vieux (duree en s)
87
// et le cas echeant le touch() ; renvoie true si la condition est verifiee
88
// et fait touch() sauf si ca n'est pas souhaite
89
// (regle aussi le probleme des droits sur les fichiers touch())
90

    
91
if (!defined('GLPI_ROOT')){
92
        die("Sorry. You can't access directly to this file");
93
        }
94

    
95
/// Cron class
96
class Cron {
97

    
98
        /// Array of defined tasks
99
        var $taches=array(); 
100

    
101
        /**
102
         * Constructor
103
         * @param $taches  task array for manual use
104
         **/
105
        function Cron($taches=array()){
106
                global $CFG_GLPI;
107
                if(count($taches)>0){
108
                        $this->taches=$taches;
109
                }else{
110
                        // la cle est la tache, la valeur le temps minimal, en secondes, entre
111
                        // deux memes taches ex $this->taches["test"]=30;
112

    
113
                        if ($CFG_GLPI["ocs_mode"]){
114
                                // Every 5 mns
115
                                $this->taches["ocsng"]=300;
116
                        }
117
                        // Mailing alerts if mailing activated
118
                        if ($CFG_GLPI["mailing"]){
119
                                if ($CFG_GLPI["cartridges_alert"]>0)
120
                                        $this->taches["cartridge"]=$CFG_GLPI["cartridges_alert"];
121
                                if ($CFG_GLPI["consumables_alert"]>0)
122
                                        $this->taches["consumable"]=$CFG_GLPI["consumables_alert"];
123
                        }
124
                        if ($CFG_GLPI["licenses_alert"]>0){
125
                                $this->taches["software"]=DAY_TIMESTAMP;
126
                        }
127

    
128
                        $this->taches["contract"]=DAY_TIMESTAMP;
129
                        $this->taches["infocom"]=DAY_TIMESTAMP;
130
                        $this->taches["logs"]=DAY_TIMESTAMP;
131
                        $this->taches["optimize"]=DAY_TIMESTAMP;
132

    
133
                        $this->taches["mailgate"]=600;
134
                        $this->taches["dbreplicate"]=300;
135
                        
136
                        // Auto update check
137
                        if ($CFG_GLPI["auto_update_check"]>0){
138
                                $this->taches["check_update"]=$CFG_GLPI["auto_update_check"]*DAY_TIMESTAMP;
139
                        }
140
                        // Garbage collector for expired file cache
141
                        if ($CFG_GLPI["use_cache"]){
142
                                $this->taches["cache"]=DAY_TIMESTAMP;
143
                        }
144
                        //Garbage collector for expired session file
145
                        $this->taches["session"]=DAY_TIMESTAMP;
146
                        //Plugins cron  
147
                        $cronplug=getPluginsCronJobs(); 
148
                        if (is_array($cronplug)&&count($cronplug)){ 
149
                                $this->taches=array_merge($this->taches,$cronplug); 
150
                        } 
151
                }
152
                        
153
                        
154
                
155
        }
156

    
157
        /**
158
         * Launch cron
159
         **/
160
        function launch() {
161

    
162
                global $CFG_GLPI,$LANG;
163

    
164
                $t = time();
165

    
166
                // Quelle est la tache la plus urgente ?
167
                $tache = FALSE;
168
                $tmin = $t;
169

    
170

    
171
                foreach ($this->taches as $nom => $periode) {
172
                        $lock = GLPI_CRON_DIR. '/' . $nom . '.lock';
173
                        if (file_exists($lock)){
174
                                $date_lock = @filemtime($lock);
175
                        } else {
176
                                $date_lock=0;
177
                        }
178
                        if ($date_lock + $periode < $tmin) {
179
                                $tmin = $date_lock + $periode;
180
                                $tache = $nom;
181
                                $last = $date_lock;
182
                        }
183
                        // debug : si la date du fichier est superieure a l'heure actuelle,
184
                        // c'est que le serveur a (ou a eu) des problemes de reglage horaire
185
                        // qui peuvent mettre en peril les taches cron : signaler dans le log
186
                        // (On laisse toutefois flotter sur une heure, pas la peine de s'exciter
187
                        // pour si peu)
188
                        //                else if ($date_lock > $t + HOUR_TIMESTAMP)
189
                        //echo "Erreur de date du fichier $lock : $date_lock > $t !";
190
                }
191
                if (!$tache) return;
192

    
193
                // Interdire des taches paralleles, de maniere a eviter toute concurrence
194
                // entre deux appli partageant la meme base, ainsi que toute interaction
195
                // bizarre entre des taches differentes
196
                // Ne rien lancer non plus si serveur naze evidemment
197

    
198
                if (!$this->get_lock('cron')) {
199
                        //echo "tache $tache: pas de lock cron";
200
                        return;
201
                }
202

    
203
                // Un autre lock dans _DIR_SESSIONS, pour plus de securite
204
                $lock = GLPI_CRON_DIR. '/'. $tache . '.lock';
205
                if ($this->touch($lock, $this->taches[$tache])) {
206
                        // preparer la tache
207
                        $this->timer('tache');
208

    
209
                        $fonction = 'cron_' . $tache;
210

    
211
                        $fct_trouve=false;
212
                        if (!function_exists($fonction)){
213
                                // pas trouvé de fonction -> inclusion de la fonction 
214
                                if(file_exists(GLPI_ROOT.'/inc/'.$tache.'.function.php')) include_once(GLPI_ROOT.'/inc/'.$tache.'.function.php');
215
                                if(file_exists(GLPI_ROOT.'/inc/'.$tache.'.class.php')) include_once(GLPI_ROOT.'/inc/'.$tache.'.class.php');
216

    
217
                        } else { $fct_trouve=true;}
218

    
219
                        if ($fct_trouve||function_exists($fonction)){
220
                                // la fonction a été inclus ou la fonction existe
221
                                // l'appeler
222
                                logInFile("cron","Launch $tache\n");
223
                                $code_de_retour = $fonction($last);
224

    
225
                                // si la tache a eu un effet : log
226
                                if ($code_de_retour) {
227
                                        //echo "cron: $tache (" . $this->timer('tache') . ")";
228
                                        // eventuellement modifier la date du fichier
229

    
230
                                        if ($code_de_retour < 0) {
231
                                                @touch($lock, (0 - $code_de_retour));
232
                                        } else {// Log Event 
233
//                                                logEvent("-1", "system", 3, "cron", $tache." (" . $this->timer('tache') . ") ".$LANG["log"][45] );
234
                                                logInFile("cron","$tache Successfull (" . $this->timer('tache') . ")\n");
235
                                        }
236
                                } else {
237
                                        logInFile("cron","$tache Nothing to do (" . $this->timer('tache') . ")\n");
238
                                }
239

    
240
                        } else {echo "Erreur fonction manquante";}
241

    
242

    
243

    
244

    
245
                }
246

    
247
                // relacher le lock mysql
248
                $this->release_lock('cron');
249
        }
250

    
251

    
252
        /**
253
         * Touch a file : set time of a file and return if file was last touch before the defined date
254
         * @param $fichier file to touch
255
         * @param $duree delay in past to touch the file (0: now)
256
         * @param $touch do touch action ?
257
         **/
258
        function touch($fichier, $duree=0, $touch=true) {
259
                if (!($exists = @is_readable($fichier))
260
                                || ($duree == 0)
261
                                || (@filemtime($fichier) < time() - $duree)) {
262
                        if ($touch) {
263
                                if (!@touch($fichier)) { @unlink($fichier); @touch($fichier); };
264
                                if (!$exists) @chmod($fichier, 0666);
265
                        }
266
                        return true;
267
                }
268
                return false;
269
        }
270

    
271

    
272

    
273

    
274
        /**
275
         * Timer used to computer time of a process
276
         * Launch twice to computer the delay
277
         * @param $t timer name used
278
         **/
279
        function timer($t='rien') {
280
                static $time;
281
                $a=time(); $b=microtime();
282

    
283
                if (isset($time[$t])) {
284
                        $p = $a + $b - $time[$t];
285
                        unset($time[$t]);
286
                        return sprintf("%.2fs", $p);
287
                } else
288
                        $time[$t] = $a + $b;
289
        }
290

    
291

    
292

    
293
        /** Set a local lock
294
        *@param $nom lock name
295
        *@param $timeout lock timeout
296
        */
297
        function get_lock($nom, $timeout = 0) {
298
                global $DB, $CFG_GLPI;
299

    
300
                // Changer de nom toutes les heures en cas de blocage MySQL (ca arrive)
301
                define('_LOCK_TIME', intval(time()/HOUR_TIMESTAMP-316982));
302
                $nom .= _LOCK_TIME;
303

    
304
                $nom = addslashes($nom);
305
                $query = "SELECT GET_LOCK('$nom', $timeout)";
306
                $result = $DB->query($query);
307
                list($lock_ok) = $DB->fetch_array($result);
308

    
309
                if (!$lock_ok) log("pas de lock sql pour $nom");
310
                return $lock_ok;
311
        }
312

    
313
        /** Unets a local lock
314
        *@param $nom lock name
315
        */
316
        function release_lock($nom) {
317
                global $DB,$CFG_GLPI;
318

    
319
                $nom .= _LOCK_TIME;
320

    
321
                $nom = addslashes($nom);
322
                $query = "SELECT RELEASE_LOCK('$nom')";
323
                $result = $DB->query($query);
324
        }
325

    
326

    
327

    
328

    
329

    
330
}
331

    
332
?>
Redmine Appliance - Powered by TurnKey Linux