Salome HOME
- Nouvelle version de Jean-Philippe ARGAUD
[modules/adao.git] / src / daComposant / daCore / Logging.py
1 #-*-coding:iso-8859-1-*-
2 #
3 #  Copyright (C) 2008-2010  EDF R&D
4 #
5 #  This library is free software; you can redistribute it and/or
6 #  modify it under the terms of the GNU Lesser General Public
7 #  License as published by the Free Software Foundation; either
8 #  version 2.1 of the License.
9 #
10 #  This library is distributed in the hope that it will be useful,
11 #  but WITHOUT ANY WARRANTY; without even the implied warranty of
12 #  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13 #  Lesser General Public License for more details.
14 #
15 #  You should have received a copy of the GNU Lesser General Public
16 #  License along with this library; if not, write to the Free Software
17 #  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
18 #
19 #  See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
20 #
21 __doc__ = """
22     Ce module permet de mettre en place un logging utilisable partout dans
23     l'application, par défaut à la console, et si nécessaire dans un fichier.
24     
25     Il doit être appelé en premier dans AssimilationStudy (mais pas directement
26     dans les applications utilisateurs), en l'important et en instanciant un
27     objet :
28         import Logging ; Logging.Logging()
29
30     Par défaut, seuls les messages du niveau WARNING ou au-delà sont disponibles
31     (donc les simples messages d'info ne sont pas disponibles), ce que l'on peut
32     changer à l'instanciation avec le mot-clé "level" :
33         import Logging ; Logging.Logging(level=20)
34
35     On peut éventuellement demander à l'objet de sortir aussi les messages dans
36     un fichier (noms par défaut : AssimilationStudy.log, niveau NOTSET) :
37         import Logging ; Logging.Logging().setLogfile()
38
39     Si on veut changer le nom du fichier ou le niveau global de message, il faut
40     récupérer l'instance et appliquer les méthodes :
41         import Logging
42         log = Logging.Logging()
43         import logging
44         log.setLevel(logging.DEBUG)
45         log.setLogfile(filename="toto.log", filemode="a", level=logging.WARNING)
46     et on change éventuellement le niveau avec :
47         log.setLogfileLevel(logging.INFO)
48     
49     Ensuite, n'importe où dans les applications, il suffit d'utiliser le module
50     "logging" (avec un petit "l") :
51         import logging
52         log = logging.getLogger(NAME) # Avec rien (recommandé) ou un nom NAME
53         log.critical("...")
54         log.error("...")
55         log.warning("...")
56         log.info("...")
57         log.debug("...")
58     ou encore plus simplement :
59         import logging
60         logging.info("...")
61
62     Dans une application, à n'importe quel endroit et autant de fois qu'on veut,
63     on peut changer le niveau global de message en utilisant par exemple :
64         import logging
65         logging.setLevel(logging.DEBUG)
66     
67     On rappelle les niveaux (attributs de "logging") et leur ordre :
68         NOTSET=0 < DEBUG=10 < INFO=20 < WARNING=30 < ERROR=40 < CRITICAL=50
69 """
70 __author__ = "Jean-Philippe ARGAUD - Octobre 2008"
71
72 import os
73 import sys
74 import logging
75 from PlatformInfo import PlatformInfo
76
77 LOGFILE = os.path.join(os.path.abspath(os.curdir),"AssimilationStudy.log")
78
79 # ==============================================================================
80 class Logging:
81     def __init__(self, level=logging.WARNING):
82         """
83         Initialise un logging à la console pour TOUS les niveaux de messages.
84         """
85         logging.basicConfig(
86             format = '%(levelname)-8s %(message)s',
87             level  = level,
88             stream = sys.stdout,
89             )
90         self.__logfile = None
91         #
92         # Initialise l'affichage de logging
93         # ---------------------------------
94         p = PlatformInfo()
95         #
96         logging.info( "--------------------------------------------------" )
97         logging.info( "Lancement de "+p.getName()+" "+p.getVersion() )
98         logging.info( "--------------------------------------------------" )
99         logging.info( "Versions logicielles :" )
100         logging.info( "- Python "+p.getPythonVersion() )
101         logging.info( "- Numpy "+p.getNumpyVersion() )
102         logging.info( "- Scipy "+p.getScipyVersion() )
103         logging.info( "" )
104
105     def setLogfileLevel(self, level=logging.NOTSET ):
106         """
107         Permet de changer globalement le niveau des messages disponibles.
108         """
109         logging.getLogger().setLevel(level)
110
111     def setLogfile(self, filename=LOGFILE, filemode="w", level=logging.NOTSET):
112         """
113         Permet de disposer des messages dans un fichier EN PLUS de la console.
114         """
115         if self.__logfile is not None:
116             # Supprime le précédent mode de stockage fichier s'il exsitait
117             logging.getLogger().removeHandler(self.__logfile)
118         self.__logfile = logging.FileHandler(filename, filemode)
119         self.__logfile.setLevel(level)
120         self.__logfile.setFormatter(
121             logging.Formatter('%(asctime)s %(levelname)-8s %(message)s',
122                               '%d %b %Y %H:%M:%S'))
123         logging.getLogger().addHandler(self.__logfile)
124
125     def setLogfileLevel(self, level=logging.NOTSET ):
126         """
127         Permet de changer le niveau des messages stockés en fichier. Il ne sera
128         pris en compte que s'il est supérieur au niveau global.
129         """
130         self.__logfile.setLevel(level)
131     
132     def getLevel(self):
133         """
134         Renvoie le niveau de Logging sous forme texte
135         """
136         return logging.getLevelName( logging.getLogger().getEffectiveLevel() )
137
138 # ==============================================================================
139 if __name__ == "__main__":
140     print '\n AUTODIAGNOSTIC \n'
141     import os.path
142
143     l = Logging(level = logging.NOTSET)
144     
145     logging.info("Message numéro 1 uniquement disponible sur console")
146     
147     l.setLogfile(level = logging.WARNING)
148     if not os.path.isfile(LOGFILE):
149         raise ValueError("Le fichier de log \"%s\" n'a pas pu être créé."%LOGFILE)
150     
151     logging.info("Message numéro 2 uniquement disponible sur console")
152     logging.warning("Message numéro 3 conjointement disponible sur console et fichier")
153     
154     l.setLogfileLevel(logging.INFO)
155     
156     logging.info("Message numéro 4 conjointement disponible sur console et fichier")
157     
158     print
159     print " Le logging a été correctement initialisé. Le fichier suivant"
160     print "   %s"%os.path.basename(LOGFILE)
161     print " a été correctement créé, et peut être effacé après vérification."
162     print