Package cheesecake :: Module logger
[hide private]
[frames] | no frames]

Source Code for Module cheesecake.logger

  1  import sys, re 
  2   
  3  ######################################################## 
  4  ############### PRODUCERS ############################## 
  5  ######################################################## 
  6   
7 -class Message(object):
8 - def __init__(self, keywords, args):
9 self.keywords = keywords 10 self.args = args
11
12 - def content(self):
13 return " ".join(map(str, self.args)) 14
15 - def prefix(self):
16 return "[%s] " % (":".join(self.keywords)) 17
18 - def __str__(self):
19 return self.prefix() + self.content() 20
21 -class Producer(object):
22 """ Log producer API which sends messages to be logged 23 to a 'consumer' object, which then prints them to stdout, 24 stderr, files, etc. 25 """ 26 27 Message = Message # to allow later customization 28 keywords2consumer = {} 29
30 - def __init__(self, keywords):
31 if isinstance(keywords, str): 32 keywords = tuple(keywords.split()) 33 self.keywords = keywords
34
35 - def __repr__(self):
36 return "<Producer %s>" % ":".join(self.keywords)
37
38 - def __getattr__(self, name):
39 if name[0] == '_': 40 raise AttributeError, name 41 producer = self.__class__(self.keywords + (name,)) 42 setattr(self, name, producer) 43 return producer
44
45 - def __call__(self, *args):
46 func = self._getconsumer(self.keywords) 47 if func is not None: 48 func(self.Message(self.keywords, args))
49
50 - def _getconsumer(self, keywords):
51 for i in range(len(self.keywords), 0, -1): 52 try: 53 return self.keywords2consumer[self.keywords[:i]] 54 except KeyError: 55 continue 56 return self.keywords2consumer.get('default', default_consumer)
57 58 default = Producer('default') 59
60 -def default_consumer(msg):
61 print str(msg) 62 63 Producer.keywords2consumer['default'] = default_consumer 64
65 -class MultipleProducer(Producer):
66
67 - def __call__(self, *args, **kwargs):
68 for func in self._getconsumer(self.keywords): 69 if func is not None: 70 return func(self.Message(self.keywords, args), **kwargs)
71
72 - def _getconsumer(self, keywords):
73 found_consumer = False 74 for keyword in keywords: 75 consumer = self.keywords2consumer.get((keyword,)) 76 found_consumer = True 77 yield consumer 78 if not found_consumer: 79 yield self.keywords2consumer.get('default', default_consumer)
80 81 ######################################################## 82 ############### CONSUMERS ############################## 83 ######################################################## 84
85 -class File(object):
86 - def __init__(self, f):
87 assert hasattr(f, 'write') 88 assert isinstance(f, file) or not hasattr(f, 'open') 89 self._file = f 90
91 - def __call__(self, msg):
92 print >>self._file, str(msg) 93
94 -class Path(File):
95 - def __init__(self, filename, append=False):
96 mode = append and 'a' or 'w' 97 f = open(str(filename), mode, buffering=1) 98 super(Path, self).__init__(f) 99
100 -def STDOUT(msg):
101 print >>sys.stdout, str(msg) 102
103 -def STDERR(msg):
104 print >>sys.stderr, str(msg) 105
106 -def setconsumer(keywords, consumer):
107 # normalize to tuples 108 if isinstance(keywords, str): 109 keywords = tuple(map(None, keywords.split())) 110 elif not isinstance(keywords, tuple): 111 raise TypeError("key %r is not a string or tuple" % (keywords,)) 112 if consumer is not None and not callable(consumer): 113 if not hasattr(consumer, 'write'): 114 raise TypeError("%r should be None, callable or file-like" % (consumer,)) 115 consumer = File(consumer) 116 #print "setting consumer for " + str(keywords) + "to " + str(consumer) 117 Producer.keywords2consumer[keywords] = consumer 118