]> snippets.scripts.mit.edu Git - Scripts/git/.git/blame - barn-growl/barn-growl.py
kdo: Upstream krb5 now supports kswitch
[Scripts/git/.git] / barn-growl / barn-growl.py
CommitLineData
e9647132
PI
1#!/usr/bin/env python
2
9d9c1ae1
PI
3"""
4Subscribes to zephyr via tzc and sends messages to notification drivers (growl or libnotify).
5"""
6
e9647132
PI
7import sexpr
8import os
9d9c1ae1 9import subprocess
e9647132
PI
10import fcntl
11import select
12import sys
13from abstfilter import AbstractConsumer
9d9c1ae1 14import optparse
8332cda6 15import time
e9647132 16
9d9c1ae1
PI
17class Notifier(AbstractConsumer):
18 def __init__(self, usegrowl, usenotify, useprint):
19 self.usegrowl = usegrowl
20 self.usenotify = usenotify
2deb9d01
GT
21 if usenotify:
22 import pynotify
23 pynotify.init("Zephyr")
24 self.pings = {}
f9d64b9d 25 self.pynotify = pynotify
9d9c1ae1 26 self.useprint = useprint
e9647132
PI
27 return
28 def feed(self, s):
29 if s is None or type(s) is type(''): return
e9647132
PI
30 d = dict([(ss[0], len(ss) > 2 and ss[2] or None) for ss in s])
31 if d['tzcspew'] == 'message':
32 zclass = d['class'].lower()
33 zinstance = d['instance'].lower()
34 zop = d['opcode'].lower()
35 zsender = d['sender'].lower()
36 zauth = d['auth'].lower() == 'yes'
8332cda6 37 ztime = "%02d:%02d" % time.strptime(d['time'])[3:5]
e9647132 38 zmessage = d['message']
de9408d7
GT
39 idtuple = (zclass, zinstance, zsender, ztime)
40 id = '%s/\n%s/\n%s\n %s' % idtuple
e9647132
PI
41 if zop == 'ping':
42 header = '%s (%s)' % (id, zsender)
43 message = '...'
44 elif zop == 'nil':
9d9c1ae1
PI
45 header = '%s (%s)' % (id, len(zmessage) > 0 and zmessage[0] or zsender)
46 message = '%s' % (len(zmessage) > 1 and zmessage[1] or '')
e9647132
PI
47 else:
48 return
9d9c1ae1
PI
49 if self.useprint:
50 print (id, header)
51 print message
52 if self.usegrowl:
7f245c30 53 growlnotify = ['growlnotify', '-H', 'localhost', '-a', 'MacZephyr', '-n', 'zephyr', '-d', id, '-t', header]
9d9c1ae1
PI
54 g = subprocess.Popen(growlnotify, stdin=subprocess.PIPE)
55 g.stdin.write(message)
56 g.stdin.close()
57 if self.usenotify:
de9408d7
GT
58 if idtuple in self.pings:
59 self.pings[idtuple].update(header, message)
60 self.pings[idtuple].show()
61 else:
62 n = self.pynotify.Notification(header, message)
63 n.show()
64 if zop == 'ping':
65 self.pings[idtuple] = n
66 self.pings = dict(filter(lambda ((c, i, s, time), v): time == idtuple[3], self.pings.items()))
e9647132
PI
67 def close(self):
68 return
69
70def main(argv):
9d9c1ae1
PI
71 parser = optparse.OptionParser(usage = '%prog [-s "username@machine"] (--growl | --notify | --print)',
72 description = __doc__.strip())
73 parser.add_option('-s', '--ssh',
74 type = 'string',
75 default = None,
76 dest = 'ssh',
77 help = 'optional remote host to run tzc')
78 parser.add_option('-g', '--growl',
79 action = 'store_true',
80 default = False,
81 dest = 'growl',
82 help = 'use growlnotify for output')
83 parser.add_option('-n', '--notify',
84 action = 'store_true',
85 default = False,
86 dest = 'notify',
87 help = 'use notify-send for output')
88 parser.add_option('-p', '--print',
89 action = 'store_true',
90 default = False,
91 dest = 'useprint',
92 help = 'use stdout for output')
93 opts, args = parser.parse_args()
e9647132 94
9d9c1ae1
PI
95 usegrowl = opts.growl
96 usenotify = opts.notify
97 useprint = opts.useprint
98 if not usegrowl and not usenotify and not useprint:
99 parser.print_help(sys.stderr)
100 return 1
101 ssh = opts.ssh
e9647132 102
c0557112
PI
103 if ssh is None:
104 retval = subprocess.call(['which', 'tzc'], stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
105 if retval:
106 print 'tzc not in path. Please add -s username@machine to specify remote host.'
107 return 1
108
9d9c1ae1 109 if ssh is not None:
92369cd9 110 command = "ssh -o GSSAPIAuthentication=yes -o GSSAPIDelegateCredentials=yes -o GSSAPIKeyExchange=yes %s 'tzc -si'" % ssh
9d9c1ae1
PI
111 else:
112 command = "tzc -si"
113 p = os.popen(command)
114 r = sexpr.SExprReader(Notifier(usegrowl, usenotify, useprint))
e9647132
PI
115
116 flags = fcntl.fcntl(p, fcntl.F_GETFL)
117 fcntl.fcntl(p, fcntl.F_SETFL, flags | os.O_NONBLOCK)
118
c0557112
PI
119 try:
120 while 1:
121 [i,o,e] = select.select([p], [], [], 5)
122 if i: s = p.read(1024)
123 else: s = ''
e9647132 124
c0557112
PI
125 if s != '':
126 r.feed(s)
127 except KeyboardInterrupt:
128 pass
e9647132
PI
129 return 0
130
131if __name__ == "__main__":
132 sys.exit(main(sys.argv))