This repository has been archived by the owner on Jan 3, 2023. It is now read-only.
/
debothena.py
executable file
·104 lines (90 loc) · 2.93 KB
/
debothena.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
#!/usr/bin/python
import re
import urllib
from lxml import etree
import time
import sys
from random import choice
import os
try:
import zephyr
except ImportError:
import site
site.addsitedir('/mit/broder/lib/python%s/site-packages' % sys.version[:3])
import zephyr
last_seen = {}
seen_timeout = 5 * 60
parser = etree.HTMLParser(encoding='UTF-8')
def build_matcher(regex, flags=0):
r = re.compile(regex, flags)
def match(zgram):
return r.findall(zgram.fields[-1])
return match
matchers = (
('Debathena', [build_matcher(r'\btrac[-\s:]*#([0-9]{1,5})\b', re.I)]),
('Debathena', [build_matcher(r'#([0-9]{1,5})\b')])
)
def fetch_debathena(ticket):
u = 'http://debathena.mit.edu/trac/ticket/%s' % ticket
f = urllib.urlopen(u)
t = etree.parse(f, parser)
title = t.xpath('string(//h2[@class])')
if title:
return u, title
else:
return u, None
fetchers = {
'Debathena': fetch_debathena,
}
def find_ticket_info(zgram):
for tracker, ms in matchers:
for m in ms:
ticket = m(zgram)
for t in ticket:
yield tracker, t
def undebathena_fun():
u = 'http://debathena.mit.edu/trac/wiki/PackageNamesWeDidntUse'
f = urllib.urlopen(u)
t = etree.parse(f, parser)
package = choice(t.xpath('id("content")//li')).text.strip()
dir = choice(['/etc', '/bin', '/usr/bin', '/sbin', '/usr/sbin',
'/dev/mapper', '/etc/default', '/var/run'])
file = choice(os.listdir(dir))
return u, "%s should divert %s/%s" % (package, dir, file)
def main():
zephyr.init()
subs = zephyr.Subscriptions()
subs.add(('broder-test', '*', '*'))
subs.add(('debathena', '*', '*'))
subs.add(('undebathena', '*', '*'))
while True:
zgram = zephyr.receive(True)
if not zgram:
continue
if zgram.opcode.lower() == 'kill':
sys.exit(0)
messages = []
for tracker, ticket in find_ticket_info(zgram):
fetcher = fetchers.get(tracker)
if fetcher:
if (zgram.opcode.lower() != 'auto' and
last_seen.get((tracker, ticket, zgram.cls), 0) < time.time() - seen_timeout):
if zgram.cls == 'undebathena':
u, t = undebathena_fun()
else:
u, t = fetcher(ticket)
if not t:
t = 'Unable to identify ticket %s' % ticket
messages.append('%s ticket %s: %s' % (tracker, ticket, t))
last_seen[(tracker, ticket, zgram.cls)] = time.time()
if messages:
z = zephyr.ZNotice()
z.cls = zgram.cls
z.instance = zgram.instance
z.recipient = zgram.recipient
z.opcode = 'auto'
z.sender = 'debothena'
z.fields = [u, '\n'.join(messages)]
z.send()
if __name__ == '__main__':
main()