adkfasdyfb
This commit is contained in:
@ -14,7 +14,7 @@
|
||||
###
|
||||
|
||||
import sys
|
||||
sys.path.append('/home/dennis/public_html')
|
||||
sys.path.append('/var/www/bots.ubuntulinux.nl')
|
||||
from commoncgi import *
|
||||
import lp_auth
|
||||
import sha
|
||||
@ -30,6 +30,10 @@ cur = con.cursor()
|
||||
# Login check
|
||||
person = None
|
||||
error = ''
|
||||
anonymous = form.has_key('anonymous')
|
||||
anonlink = ''
|
||||
if anonymous:
|
||||
anonlink = '&anonymous=1';
|
||||
|
||||
# Delete old sessions
|
||||
cur.execute("""DELETE FROM sessions WHERE time < %d""", int(time.time()) - 2592000 * 3)
|
||||
@ -127,12 +131,10 @@ if not person and form.has_key('user') and form.has_key('pw'):
|
||||
error = "You are not in the '%s' group on launchpad" % lp_group
|
||||
|
||||
# Not authenticated.
|
||||
if not person or not person.authenticated:
|
||||
if not (person and person.authenticated) and not anonymous:
|
||||
if error:
|
||||
print """<span style="color:red">%s</span>""" % error
|
||||
print """<form action="/bans.cgi" method="post">
|
||||
<b>The old launchpad based authentication system has been
|
||||
disabled!</b><br /><br />
|
||||
Login:<br />
|
||||
<input class="input" type="text" name="user" /><br />
|
||||
Password:<br />
|
||||
@ -148,6 +150,7 @@ if not person or not person.authenticated:
|
||||
<input class="input" type="text" name="lpmail" /><br /><br />
|
||||
<input class="submit" type="submit" value="Request password" />
|
||||
</form>
|
||||
<a href="/bans.cgi?anonymous=1">Browse the bantracker anonymously</a>
|
||||
"""
|
||||
send_page('bans.tmpl')
|
||||
|
||||
@ -161,7 +164,7 @@ if form.has_key('log'):
|
||||
|
||||
# Main page
|
||||
# Process comments
|
||||
if form.has_key('comment') and form.has_key('comment_id'):
|
||||
if form.has_key('comment') and form.has_key('comment_id') and not anonymous:
|
||||
cur.execute("""SELECT ban_id FROM comments WHERE ban_id=%s and comment=%s""", (form['comment_id'].value, form['comment'].value))
|
||||
comm = cur.fetchall()
|
||||
if not len(comm):
|
||||
@ -171,9 +174,14 @@ if form.has_key('comment') and form.has_key('comment_id'):
|
||||
|
||||
# Write the page
|
||||
print '<form action="bans.cgi" method="POST">'
|
||||
if anonymous:
|
||||
print '<input type="hidden" name="anonymous" value="1" />'
|
||||
|
||||
# Personal data
|
||||
print '<div class="pdata"> Logged in as: %s <br /> Timezone: ' % person.name
|
||||
print '<div class="pdata">'
|
||||
if not anonymous:
|
||||
print 'Logged in as: %s <br /> ' % person.name
|
||||
print 'Timezone: '
|
||||
if form.has_key('tz') and form['tz'].value in pytz.common_timezones:
|
||||
tz = form['tz'].value
|
||||
elif cookie.has_key('tz') and cookie['tz'].value in pytz.common_timezones:
|
||||
@ -188,28 +196,32 @@ for zone in pytz.common_timezones:
|
||||
print ' selected="selected"'
|
||||
print ">%s</option>" % zone
|
||||
print '</select><input class="submit" type="submit" value="change" /></form><br />'
|
||||
if form.has_key('pw1') and form.has_key('pw2'):
|
||||
pw1 = form['pw1'].value; pw2 = form['pw2'].value
|
||||
if pw1 and pw2:
|
||||
if pw1 != pw2:
|
||||
print "Passwords don't match!<br />"
|
||||
else:
|
||||
cur.execute("SELECT salt FROM users WHERE username = %s", person.nick)
|
||||
salt = cur.fetchall()[0][0]
|
||||
cur.execute("UPDATE USERS SET password = %s WHERE username = %s",
|
||||
(sha.new(salt + sha.new(pw1 + salt).hexdigest().lower()).hexdigest().lower(), person.nick))
|
||||
con.commit()
|
||||
print '<form action="bans.cgi" method="POST">'
|
||||
print 'Password: '
|
||||
print '<input class="input" type="password" name="pw1" size="10"/>'
|
||||
print '<input class="input" type="password" name="pw2" size="10"/>'
|
||||
print '<input class="submit" type="submit" value="change" /></form></div>'
|
||||
if not anonymous:
|
||||
if form.has_key('pw1') and form.has_key('pw2'):
|
||||
pw1 = form['pw1'].value; pw2 = form['pw2'].value
|
||||
if pw1 and pw2:
|
||||
if pw1 != pw2:
|
||||
print "Passwords don't match!<br />"
|
||||
else:
|
||||
cur.execute("SELECT salt FROM users WHERE username = %s", person.nick)
|
||||
salt = cur.fetchall()[0][0]
|
||||
cur.execute("UPDATE USERS SET password = %s WHERE username = %s",
|
||||
(sha.new(salt + sha.new(pw1 + salt).hexdigest().lower()).hexdigest().lower(), person.nick))
|
||||
con.commit()
|
||||
print '<form action="bans.cgi" method="POST">'
|
||||
print 'Password: '
|
||||
print '<input class="input" type="password" name="pw1" size="10"/>'
|
||||
print '<input class="input" type="password" name="pw2" size="10"/>'
|
||||
print '<input class="submit" type="submit" value="change" /></form>'
|
||||
print '</div>'
|
||||
|
||||
tz = pytz.timezone(tz)
|
||||
|
||||
# Search form
|
||||
print '<div class="search">'
|
||||
print '<form action="/bans.cgi" method="GET">'
|
||||
if anonymous:
|
||||
print '<input type="hidden" name="anonymous" value="1" />'
|
||||
print '<input class="input" type="text" name="query"'
|
||||
if form.has_key('query'):
|
||||
print 'value="%s" ' % form['query'].value
|
||||
@ -254,7 +266,7 @@ if not form.has_key('query'):
|
||||
cur.execute('SELECT COUNT(id) FROM bans')
|
||||
nump = math.ceil(int(cur.fetchall()[0][0]) / float(num_per_page))
|
||||
for i in range(nump):
|
||||
print '<a href="bans.cgi?page=%d%s">%d</a> ·' % (i, sort, i+1)
|
||||
print '<a href="bans.cgi?page=%d%s%s">%d</a> ·' % (i, sort, anonlink, i+1)
|
||||
print '</div>'
|
||||
|
||||
# Empty log div, will be filled with AJAX
|
||||
@ -270,7 +282,7 @@ for h in [['Channel',0], ['Nick/Mask',1], ['Operator',2], ['Time',6]]:
|
||||
if v < 10: h[1] += 10
|
||||
except:
|
||||
pass
|
||||
print '<th><a href="bans.cgi?sort=%s">%s</a></th>' % (h[1],h[0])
|
||||
print '<th><a href="bans.cgi?sort=%s%s">%s</a></th>' % (h[1],anonlink,h[0])
|
||||
print '<th>Log</th></tr>'
|
||||
|
||||
# Select and filter bans
|
||||
@ -373,11 +385,12 @@ for b in bans[start:end]:
|
||||
print q(c[1])
|
||||
print u' <span class="removal"><br />%s, %s</span><br />' % \
|
||||
(c[0],pickle.loads(c[2]).astimezone(tz).strftime("%b %d %Y %H:%M:%S"))
|
||||
print """<span class="pseudolink" onclick="toggle('%s','comment')">Add comment</span>""" % b[6]
|
||||
print """<div class="invisible" id="comment_%s"><br />""" % b[6]
|
||||
print """<form action="bans.cgi" method="POST"><textarea cols="50" rows="5" class="input" name="comment"></textarea><br />"""
|
||||
print """<input type="hidden" name="comment_id" value="%s" />""" % b[6]
|
||||
print """<input class="submit" type="submit" value="Send" /></form>"""
|
||||
if not anonymous:
|
||||
print """<span class="pseudolink" onclick="toggle('%s','comment')">Add comment</span>""" % b[6]
|
||||
print """<div class="invisible" id="comment_%s"><br />""" % b[6]
|
||||
print """<form action="bans.cgi" method="POST"><textarea cols="50" rows="5" class="input" name="comment"></textarea><br />"""
|
||||
print """<input type="hidden" name="comment_id" value="%s" />""" % b[6]
|
||||
print """<input class="submit" type="submit" value="Send" /></form>"""
|
||||
print '</td></tr>'
|
||||
|
||||
print '</table>'
|
||||
|
@ -21,3 +21,5 @@ def configure(advanced):
|
||||
Bantracker = conf.registerPlugin('Bantracker')
|
||||
conf.registerChannelValue(conf.supybot.plugins.BanTracker, 'enabled',
|
||||
registry.Boolean(False, """Enable the bantracker"""))
|
||||
conf.registerChannelValue(conf.supybot.plugins.BanTracker, 'stats',
|
||||
registry.Boolean(False, """Enable join/part stats"""))
|
||||
|
@ -50,6 +50,7 @@ import supybot.ircutils as ircutils
|
||||
import supybot.callbacks as callbacks
|
||||
import supybot.ircmsgs as ircmsgs
|
||||
import supybot.conf as conf
|
||||
import supybot.world as world
|
||||
|
||||
import sqlite, pytz, cPickle, datetime, time
|
||||
|
||||
@ -84,6 +85,8 @@ class Bantracker(callbacks.Plugin):
|
||||
self.lastMsgs = {}
|
||||
self.lastStates = {}
|
||||
self.logs = {}
|
||||
for channel in irc.state.channels:
|
||||
self.doStatsLog(irc, channel, "START")
|
||||
|
||||
def __call__(self, irc, msg):
|
||||
try:
|
||||
@ -115,11 +118,14 @@ class Bantracker(callbacks.Plugin):
|
||||
s = time.strftime(format) + " " + ircutils.stripFormatting(s)
|
||||
self.logs[channel] = self.logs[channel][-199:] + [s.strip()]
|
||||
|
||||
def doStatsLog(self, irc, msg, type):
|
||||
#format = conf.supybot.log.timestampFormat()
|
||||
#print "%15s %s %s %s %s" % (msg.args[0], time.strftime(format), type,
|
||||
# msg.prefix, len(irc.state.channels[msg.args[0]].users))
|
||||
pass
|
||||
def doStatsLog(self, irc, chan, type):
|
||||
if not self.registryValue('stats', chan):
|
||||
return
|
||||
num = len(irc.state.channels[chan].users)
|
||||
format = conf.supybot.log.timestampFormat()
|
||||
statslog = open('/home/dennis/ubugtu/data/statslog','a')
|
||||
statslog.write("%-20s %f %s %-6s %d\n" % (chan, time.time(), time.strftime(format), type, num))
|
||||
statslog.close()
|
||||
|
||||
def doKickban(self, irc, channel, nick, target, kickmsg = None):
|
||||
if not self.registryValue('enabled', channel):
|
||||
@ -165,7 +171,8 @@ class Bantracker(callbacks.Plugin):
|
||||
for channel in msg.args[0].split(','):
|
||||
self.doLog(irc, channel,
|
||||
'*** %s has joined %s\n' % (msg.nick or msg.prefix, channel))
|
||||
self.doStatsLog(irc, msg, "JOIN")
|
||||
if irc.prefix != msg.prefix:
|
||||
self.doStatsLog(irc, msg.args[0], "JOIN")
|
||||
|
||||
def doKick(self, irc, msg):
|
||||
if len(msg.args) == 3:
|
||||
@ -180,7 +187,7 @@ class Bantracker(callbacks.Plugin):
|
||||
self.doLog(irc, channel,
|
||||
'*** %s was kicked by %s\n' % (target, msg.nick))
|
||||
self.doKickban(irc, channel, msg.nick, target, kickmsg)
|
||||
self.doStatsLog(irc, msg, "KICK")
|
||||
self.doStatsLog(irc, msg.args[0], "KICK")
|
||||
|
||||
def doPart(self, irc, msg):
|
||||
for channel in msg.args[0].split(','):
|
||||
@ -188,7 +195,8 @@ class Bantracker(callbacks.Plugin):
|
||||
if msg.args[1].startswith('requested by'):
|
||||
args = msg.args[1].split()
|
||||
self.doKickban(irc, channel, args[2].replace(':',''), msg.nick, ' '.join(args[3:])[1:-1].strip())
|
||||
self.doStatsLog(irc, msg, "PART")
|
||||
if irc.prefix != msg.prefix:
|
||||
self.doStatsLog(irc, msg.args[0], "PART")
|
||||
|
||||
def doMode(self, irc, msg):
|
||||
channel = msg.args[0]
|
||||
@ -224,7 +232,7 @@ class Bantracker(callbacks.Plugin):
|
||||
for (channel, chan) in self.lastStates[irc].channels.iteritems():
|
||||
if msg.nick in chan.users:
|
||||
self.doLog(irc, channel, '*** %s has quit IRC (%s)\n' % (msg.nick, msg.args[0]))
|
||||
self.doStatsLog(irc, msg, "QUIT")
|
||||
self.doStatsLog(irc, channel, "QUIT")
|
||||
|
||||
def outFilter(self, irc, msg):
|
||||
# Gotta catch my own messages *somehow* :)
|
||||
@ -234,5 +242,8 @@ class Bantracker(callbacks.Plugin):
|
||||
m = ircmsgs.IrcMsg(msg=msg, prefix=irc.prefix)
|
||||
self(irc, m)
|
||||
return msg
|
||||
|
||||
def do366(self, irc, msg):
|
||||
self.doStatsLog(irc, msg.args[1], "START")
|
||||
|
||||
Class = Bantracker
|
||||
|
@ -46,3 +46,7 @@ conf.registerGlobalValue(conf.supybot.plugins.Bugtracker, 'bugtrackers',
|
||||
conf.registerGlobalValue(conf.supybot.plugins.Bugtracker, 'replyWhenNotFound',
|
||||
registry.Boolean(False, """Whether to send a message when a bug could not be
|
||||
found"""))
|
||||
conf.registerChannelValue(conf.supybot.plugins.Bugtracker, 'repeatdelay',
|
||||
registry.Integer(60, """Number of seconds to wait between repeated bug calls"""))
|
||||
conf.registerChannelValue(conf.supybot.plugins.Bugtracker, 'showassignee',
|
||||
registry.Boolean(False, """Whether to show th assignee in bug reports"""))
|
||||
|
@ -22,11 +22,16 @@ import supybot.conf as conf
|
||||
import supybot.registry as registry
|
||||
import supybot.schedule as schedule
|
||||
|
||||
import re, os, time
|
||||
import re, os, time, imaplib, commands
|
||||
import xml.dom.minidom as minidom
|
||||
from htmlentitydefs import entitydefs as entities
|
||||
import email.FeedParser
|
||||
|
||||
bugreporter_base = '/home/dennis/ubugtu/data/bugmail'
|
||||
imap_server = 'localhost'
|
||||
imap_user = commands.getoutput('cat /home/dennis/ubugtu/imap_user')
|
||||
imap_password = commands.getoutput('cat /home/dennis/ubugtu/imap_password')
|
||||
|
||||
def registerBugtracker(name, url='', description='', trackertype=''):
|
||||
conf.supybot.plugins.Bugtracker.bugtrackers().add(name)
|
||||
group = conf.registerGroup(conf.supybot.plugins.Bugtracker.bugtrackers, name)
|
||||
@ -98,10 +103,16 @@ class Bugtracker(callbacks.PluginRegexp):
|
||||
self.shown = {}
|
||||
self.nomailtime = 0
|
||||
|
||||
def die(self):
|
||||
try:
|
||||
schedule.removeEvent(self.name())
|
||||
except:
|
||||
pass
|
||||
|
||||
def is_ok(self, channel, tracker, bug):
|
||||
now = time.time()
|
||||
for k in self.shown.keys():
|
||||
if self.shown[k] < now - 60:
|
||||
if self.shown[k] < now - self.registryValue('repeatdelay', channel):
|
||||
self.shown.pop(k)
|
||||
if (channel, tracker, bug) not in self.shown:
|
||||
self.shown[(channel, tracker, bug)] = now
|
||||
@ -110,76 +121,64 @@ class Bugtracker(callbacks.PluginRegexp):
|
||||
|
||||
def reportnewbugs(self,irc):
|
||||
# Compile list of bugs
|
||||
#print "Reporting new bugs"
|
||||
print "Reporting new bugs"
|
||||
tracker = self.db['malone']
|
||||
bugs = {}
|
||||
fixed = {}
|
||||
for c in irc.state.channels:
|
||||
dir = self.registryValue('bugReporter', channel=c)
|
||||
if not dir:
|
||||
sc = imaplib.IMAP4_SSL(imap_server)
|
||||
sc.login(imap_user, imap_password)
|
||||
sc.select('INBOX')
|
||||
new_mail = sc.search(None, '(UNSEEN)')[1][0].split()[:20]
|
||||
for m in new_mail:
|
||||
print "Loading %s" % m
|
||||
msg = sc.fetch(m, 'RFC822')[1][0][1]
|
||||
#print msg
|
||||
fp = email.FeedParser.FeedParser()
|
||||
fp.feed(msg)
|
||||
bug = fp.close()
|
||||
#print "Mail parsed"
|
||||
# Determine bug number, component and tag
|
||||
try:
|
||||
id = int(bug['Reply-To'].split()[1])
|
||||
except:
|
||||
continue
|
||||
#print "Reporting in %s (%s)" % (c, dir)
|
||||
if dir not in bugs:
|
||||
#print "Reloading info from %s" % dir
|
||||
bugs[dir] = {}
|
||||
if dir.endswith('bugmail'):
|
||||
if len(os.listdir(os.path.join(dir,'Maildir','new'))) == 0:
|
||||
self.nomailtime += 1
|
||||
if self.nomailtime == 30:
|
||||
irc.queueMsg(ircmsgs.privmsg(c,'WARNING: No bugmail received in 30 minutes. Please poke Seveas.'))
|
||||
self.nomailtime = 0
|
||||
else:
|
||||
#irc.queueMsg(ircmsgs.privmsg('#ubuntu-bots','Seveas: your lucky number is %d' % self.nomailtime))
|
||||
self.nomailtime = 0
|
||||
for file in os.listdir(os.path.join(dir,'Maildir','new')):
|
||||
#print "Checking %s" % file
|
||||
fd = open(os.path.join(dir,'Maildir','new',file))
|
||||
_data = fd.readlines()
|
||||
fd.close()
|
||||
os.unlink(os.path.join(dir,'Maildir','new',file))
|
||||
component = ''
|
||||
data = []
|
||||
for line in _data:
|
||||
if line[0] in ' \t':
|
||||
data[-1] += '%s ' % line.strip()
|
||||
tag = bug['Delivered-To']
|
||||
tag = tag[tag.find('+')+1:tag.find('@')]
|
||||
component = bug['X-Launchpad-Bug']
|
||||
if 'component' in component:
|
||||
component = component[component.find('component=')+10:]
|
||||
component = component[:component.find(';')].replace('None','')
|
||||
else:
|
||||
component = ''
|
||||
if tag not in bugs:
|
||||
bugs[tag] = {}
|
||||
#print "Data extracted"
|
||||
if id not in bugs[tag]:
|
||||
try:
|
||||
os.makedirs(os.path.join(bugreporter_base,tag,str(int(id/1000))))
|
||||
except:
|
||||
pass
|
||||
print os.path.join(bugreporter_base,tag,str(int(id/1000)),str(id))
|
||||
if id > 58184 and not os.path.exists(os.path.join(bugreporter_base,tag,str(int(id/1000)),str(id))):
|
||||
print "New bug: %d" % id
|
||||
fd2 = open(os.path.join(bugreporter_base,tag,str(int(id/1000)),str(id)),'w')
|
||||
fd2.close()
|
||||
try:
|
||||
if component:
|
||||
bugs[tag][id] = self.get_bug(tracker, id, False)[0].replace('"','(%s) "' % component, 1)
|
||||
else:
|
||||
data.append('%s ' % line.strip())
|
||||
for line in data:
|
||||
if line.startswith('X-Launchpad-Bug:') and not component:
|
||||
if 'component' in line:
|
||||
component = line[line.find('component=')+10:]
|
||||
component = component[:component.find(';')]
|
||||
if component == 'None':
|
||||
component = ''
|
||||
if line.startswith('Reply-To:'):
|
||||
#print line
|
||||
try:
|
||||
bug = int(line.split()[2])
|
||||
try:
|
||||
os.makedirs(os.path.join(dir,str(int(bug/1000))))
|
||||
except:
|
||||
pass
|
||||
if bug > 58184 and not os.path.exists(os.path.join(dir,str(int(bug/1000)),str(bug))):
|
||||
#print "New bug: %d" % bug
|
||||
fd2 = open(os.path.join(dir,str(int(bug/1000)),str(bug)),'w')
|
||||
fd2.close()
|
||||
if bug not in bugs[dir]:
|
||||
try:
|
||||
if component:
|
||||
bugs[dir][bug] = self.get_bug(tracker, bug).replace('"','(%s) "' % component, 1)
|
||||
else:
|
||||
bugs[dir][bug] = self.get_bug(tracker, bug)
|
||||
except:
|
||||
#print "Unable to get bug %d" % b
|
||||
pass
|
||||
except:
|
||||
#raise
|
||||
pass # Ignore errors. Iz wrong mail
|
||||
break
|
||||
#print "New bugs in %s (%s): %s" % (c, dir, str(bugs[dir].keys()))
|
||||
# Now show them
|
||||
for b in sorted(bugs[dir].keys()):
|
||||
irc.queueMsg(ircmsgs.privmsg(c,'New bug: #%s' % bugs[dir][b][bugs[dir][b].find('bug ')+4:]))
|
||||
bugs[tag][id] = self.get_bug(tracker, id, False)[0]
|
||||
except:
|
||||
print "Cannot get bug %d" % id
|
||||
for c in irc.state.channels:
|
||||
tag = self.registryValue('bugReporter', channel=c)
|
||||
if not tag:
|
||||
continue
|
||||
if tag not in bugs.keys():
|
||||
print "No new bugs in %s" % tag
|
||||
continue
|
||||
print "New bugs in %s (%s): %s" % (c, tag, str(bugs[tag].keys()))
|
||||
for b in sorted(bugs[tag].keys()):
|
||||
irc.queueMsg(ircmsgs.privmsg(c,'New bug: #%s' % bugs[tag][b][bugs[tag][b].find('bug ')+4:]))
|
||||
|
||||
def add(self, irc, msg, args, name, trackertype, url, description):
|
||||
"""<name> <type> <url> [<description>]
|
||||
@ -286,7 +285,7 @@ class Bugtracker(callbacks.PluginRegexp):
|
||||
name = ''
|
||||
pass
|
||||
if not name:
|
||||
snarfTarget = self.registryValue('snarfTarget', msg.args[0])
|
||||
snarfTarget = self.registryValue('snarfTarget', msg.args[0]).lower()
|
||||
if not snarfTarget:
|
||||
return
|
||||
try:
|
||||
@ -305,7 +304,7 @@ class Bugtracker(callbacks.PluginRegexp):
|
||||
if not self.is_ok(msg.args[0],tracker, bugid):
|
||||
continue
|
||||
try:
|
||||
report = self.get_bug(tracker,bugid)
|
||||
report = self.get_bug(tracker,bugid,self.registryValue('showassignee', msg.args[0]))
|
||||
except BugtrackerError, e:
|
||||
if 'private' in str(e):
|
||||
irc.reply("Bug %d on http://launchpad.net/bugs/%d is private" % (bugid, bugid))
|
||||
@ -314,7 +313,8 @@ class Bugtracker(callbacks.PluginRegexp):
|
||||
return
|
||||
irc.error(str(e))
|
||||
else:
|
||||
irc.reply(report, prefixNick=False)
|
||||
for r in report:
|
||||
irc.reply(r, prefixNick=False)
|
||||
|
||||
#show_bug.cgi?id=|bugreport.cgi?bug=|(bugs|+bug)/|ticket/|tracker/.*aid=
|
||||
#&group_id=\d+&at_id=\d+
|
||||
@ -328,11 +328,12 @@ class Bugtracker(callbacks.PluginRegexp):
|
||||
return
|
||||
if not self.is_ok(msg.args[0],tracker, int(match.group('bug'))):
|
||||
return
|
||||
report = self.get_bug(tracker,int(match.group('bug')), do_url = False)
|
||||
report = self.get_bug(tracker,int(match.group('bug')),self.registryValue('showassignee', msg.args[0]), do_url = False)
|
||||
except BugtrackerError, e:
|
||||
irc.error(str(e))
|
||||
else:
|
||||
irc.reply(report, prefixNick=False)
|
||||
for r in report:
|
||||
irc.reply(r, prefixNick=False)
|
||||
turlSnarfer = urlSnarfer(turlSnarfer)
|
||||
|
||||
# Only useful for launchpad developers
|
||||
@ -367,16 +368,23 @@ class Bugtracker(callbacks.PluginRegexp):
|
||||
return tracker
|
||||
return None
|
||||
|
||||
def get_bug(self, tracker, id, do_url = True):
|
||||
(product, title, severity, status, url) = tracker.get_bug(id)
|
||||
severity = severity[0].upper() + severity[1:].lower()
|
||||
status = status[0].upper() + status[1:].lower()
|
||||
if not do_url:
|
||||
url = ''
|
||||
if product:
|
||||
return "%s bug %s in %s \"%s\" [%s,%s] %s" % (tracker.description, id, product,
|
||||
title, severity, status, url)
|
||||
return "%s bug %s \"%s\" [%s,%s] %s" % (tracker.description, id, title, severity, status, url)
|
||||
def get_bug(self, tracker, id, do_assignee, do_url = True):
|
||||
reports = []
|
||||
for r in tracker.get_bug(id):
|
||||
print r
|
||||
(bid, product, title, severity, status, assignee, url) = r
|
||||
severity = severity[0].upper() + severity[1:].lower()
|
||||
status = status[0].upper() + status[1:].lower()
|
||||
if not do_url:
|
||||
url = ''
|
||||
if product:
|
||||
reports.append("%s bug %s in %s \"%s\" [%s,%s] %s" % (tracker.description, bid, product,
|
||||
title, severity, status, url))
|
||||
else:
|
||||
reports.append("%s bug %s \"%s\" [%s,%s] %s" % (tracker.description, bid, title, severity, status, url))
|
||||
if do_assignee and assignee:
|
||||
reports[-1] = reports[-1] + (" - Assigned to %s" % assignee)
|
||||
return reports
|
||||
|
||||
# Define all bugtrackers
|
||||
class IBugtracker:
|
||||
@ -431,10 +439,11 @@ class Bugzilla(IBugtracker):
|
||||
pass
|
||||
component = _getnodetxt(bug_n.getElementsByTagName('component')[0])
|
||||
severity = _getnodetxt(bug_n.getElementsByTagName('bug_severity')[0])
|
||||
assignee = _getnodetxt(bug_n.getElementsByTagName('assigned_to')[0])
|
||||
except Exception, e:
|
||||
s = 'Could not parse XML returned by %s bugzilla: %s' % (self.description, e)
|
||||
raise BugtrackerError, s
|
||||
return (component, title, severity, status, "%s/show_bug.cgi?id=%d" % (self.url, id))
|
||||
return [(id, component, title, severity, status, assignee, "%s/show_bug.cgi?id=%d" % (self.url, id))]
|
||||
|
||||
class Issuezilla(IBugtracker):
|
||||
def get_bug(self, id):
|
||||
@ -458,10 +467,11 @@ class Issuezilla(IBugtracker):
|
||||
pass
|
||||
component = _getnodetxt(bug_n.getElementsByTagName('component')[0])
|
||||
severity = _getnodetxt(bug_n.getElementsByTagName('issue_type')[0])
|
||||
assignee = _getnodetxt(bug_n.getElementsByTagName('assigned_to')[0])
|
||||
except Exception, e:
|
||||
s = 'Could not parse XML returned by %s bugzilla: %s' % (self.description, e)
|
||||
raise BugtrackerError, s
|
||||
return (component, title, severity, status, "%s/show_bug.cgi?id=%d" % (self.url, id))
|
||||
return [(id, component, title, severity, status, assignee, "%s/show_bug.cgi?id=%d" % (self.url, id))]
|
||||
|
||||
class Malone(IBugtracker):
|
||||
def _parse(self, task):
|
||||
@ -516,11 +526,16 @@ class Malone(IBugtracker):
|
||||
except Exception, e:
|
||||
s = 'Could not parse data returned by %s: %s' % (self.description, e)
|
||||
raise BugtrackerError, s
|
||||
# Try and find duplicates
|
||||
t = taskdata['task']
|
||||
if '(' in t:
|
||||
t = t[:t.rfind('(') -1]
|
||||
return (t, bugdata['title'], taskdata['importance'],
|
||||
taskdata['status'], "%s/bugs/%s" % (self.url.replace('/malone',''), id))
|
||||
if bugdata['duplicate-of']:
|
||||
dupbug = self.get_bug(int(bugdata['duplicate-of']))
|
||||
return [(id, t, bugdata['title'] + (' (dup-of: %d)' % dupbug[0][0]), taskdata['importance'],
|
||||
taskdata['status'], "%s/bugs/%s" % (self.url.replace('/malone',''), id))] + dupbug
|
||||
return [(id, t, bugdata['title'], taskdata['importance'],
|
||||
taskdata['status'], taskdata['assignee'], "%s/bugs/%s" % (self.url.replace('/malone',''), id))]
|
||||
|
||||
# <rant>
|
||||
# Debbugs sucks donkeyballs
|
||||
@ -591,7 +606,7 @@ class Debbugs(IBugtracker):
|
||||
except Exception, e:
|
||||
s = 'Could not parse data returned by %s bugtracker: %s' % (self.description, e)
|
||||
raise BugtrackerError, s
|
||||
return (data['package'], data['title'], data['severity'], data['status'], "%s/%s" % (self.url, id))
|
||||
return [(id, data['package'], data['title'], data['severity'], data['status'], '', "%s/%s" % (self.url, id))]
|
||||
|
||||
# For trac based trackers we also need to do some screenscraping - should be
|
||||
# doable unless a certain track instance uses weird templates.
|
||||
@ -614,7 +629,9 @@ class Trac(IBugtracker):
|
||||
package = l[l.find('>')+1:l.find('</')]
|
||||
if 'headers="h_severity"' in l:
|
||||
severity = l[l.find('>')+1:l.find('</')]
|
||||
return (package, title, severity, status, "%s/%s" % (self.url, id))
|
||||
if 'headers="h_owner"' in l:
|
||||
assignee = l[l.find('>')+1:l.find('</')]
|
||||
return [(id, package, title, severity, status, assignee, "%s/%s" % (self.url, id))]
|
||||
|
||||
class WikiForms(IBugtracker):
|
||||
def get_bug(self, id):
|
||||
@ -624,7 +641,6 @@ class WikiForms(IBugtracker):
|
||||
return s
|
||||
|
||||
url = "%s/%05d" % (self.url, id)
|
||||
#print url
|
||||
try:
|
||||
bugdata = utils.web.getUrl(url)
|
||||
except Exception, e:
|
||||
@ -640,12 +656,14 @@ class WikiForms(IBugtracker):
|
||||
status = strip_tags(l[l.find('<dd>')+4:])
|
||||
if '<dt>category</dt>' in l2:
|
||||
package = strip_tags(l[l.find('<dd>')+4:])
|
||||
return (package, title, severity, status, "%s/%05d" % (self.url, id))
|
||||
return [(id, package, title, severity, status, '', "%s/%05d" % (self.url, id))]
|
||||
|
||||
sfre = re.compile(r"""
|
||||
.*?
|
||||
<h2>\[.*?\]\s*(?P<title>.*?)</h2>
|
||||
.*?
|
||||
Assigned To.*?<br>\s+(?P<assignee>\S+)
|
||||
.*?
|
||||
Priority.*?(?P<priority>\d+)
|
||||
.*?
|
||||
Status.*?<br>\s+(?P<status>\S+)
|
||||
@ -669,7 +687,7 @@ class Sourceforge(IBugtracker):
|
||||
resolution = reo.group('resolution')
|
||||
if not (resolution.lower() == 'none'):
|
||||
status += ' ' + resolution
|
||||
return (None, reo.group('title'), "Pri: %s" % reo.group('priority'), status, self._sf_url % id)
|
||||
return [(id, None, reo.group('title'), "Pri: %s" % reo.group('priority'), status, reo.group('assignee'),self._sf_url % id)]
|
||||
except:
|
||||
raise BugtrackerError, "Bug not found"
|
||||
|
||||
|
@ -97,14 +97,14 @@ class Encyclopedia(callbacks.PluginRegexp):
|
||||
except KeyError:
|
||||
irc.queueMsg(ircmsgs.privmsg('#ubuntu-ops', "In %s, %s said: %s" % (msg.args[0], msg.nick, msg.args[1])))
|
||||
irc.reply("Your edit request has been forwarded to #ubuntu-ops. Thank you for your attention to detail",private=True)
|
||||
lfd = open('/home/dennis/public_html/botlogs/lock','a')
|
||||
lfd = open('/var/www/bots.ubuntulinux.nl/botlogs/lock','a')
|
||||
fcntl.lockf(lfd, fcntl.LOCK_EX)
|
||||
fd = open('/home/dennis/public_html/botlogs/%s.log' % datetime.date.today().strftime('%Y-%m-%d'),'a')
|
||||
fd = open('/var/www/bots.ubuntulinux.nl/botlogs/%s.log' % datetime.date.today().strftime('%Y-%m-%d'),'a')
|
||||
fd.write("%s %-20s %-16s %s\n" % (datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S'),msg.args[0], msg.nick, msg.args[1]))
|
||||
fd.close()
|
||||
fcntl.lockf(lfd,fcntl.LOCK_UN)
|
||||
lfd.close()
|
||||
os.chmod('/home/dennis/public_html/botlogs/%s.log' % datetime.date.today().strftime('%Y-%m-%d'),0644)
|
||||
os.chmod('/var/www/bots.ubuntulinux.nl/botlogs/%s.log' % datetime.date.today().strftime('%Y-%m-%d'),0644)
|
||||
return False
|
||||
if timeout:
|
||||
for key in self.times.keys():
|
||||
|
@ -20,7 +20,8 @@ apt_pkg.init()
|
||||
|
||||
datadir = '/home/dennis/ubugtu/data/facts'
|
||||
aptdir = '/home/dennis/ubugtu/data/apt'
|
||||
distros = ('dapper','breezy','edgy','hoary','warty','dapper-commercial','dapper-seveas','breezy-seveas','dapper-imbrandon','edgy-imbrandon', 'dapper-backports','edgy-seveas')
|
||||
logdir = '/var/www/bots.ubuntulinux.nl/'
|
||||
distros = ('dapper','edgy','feisty','breezy','edgy','dapper-commercial','dapper-seveas','breezy-seveas','dapper-imbrandon','edgy-imbrandon', 'dapper-backports','edgy-seveas')
|
||||
|
||||
# Simple wrapper class for factoids
|
||||
class Factoid:
|
||||
@ -186,19 +187,6 @@ class Encyclopedia(callbacks.Plugin):
|
||||
# Big action 1: editing factoids
|
||||
if '=~' in text:
|
||||
# Editing
|
||||
if not capab(msg.prefix, 'editfactoids'):
|
||||
irc.reply("Your edit request has been forwarded to %s. Thank you for your attention to detail"%self.registryValue('relaychannel'),private=True)
|
||||
irc.queueMsg(ircmsgs.privmsg(self.registryValue('relaychannel'), "In %s, %s said: %s" % (msg.args[0], msg.nick, msg.args[1])))
|
||||
lfd = open('/home/dennis/public_html/botlogs/lock','a')
|
||||
fcntl.lockf(lfd, fcntl.LOCK_EX)
|
||||
fd = open('/home/dennis/public_html/botlogs/%s.log' % datetime.date.today().strftime('%Y-%m-%d'),'a')
|
||||
fd.write("%s %-20s %-16s %s\n" % (datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S'), channel, msg.nick, msg.args[1]))
|
||||
fd.close()
|
||||
fcntl.lockf(lfd,fcntl.LOCK_UN)
|
||||
lfd.close()
|
||||
os.chmod('/home/dennis/public_html/botlogs/%s.log' % datetime.date.today().strftime('%Y-%m-%d'),0644)
|
||||
return
|
||||
# All clear!
|
||||
# Find factoid
|
||||
p = text.find('=~')
|
||||
name, value = text[:p].strip(), text[p+2:].strip()
|
||||
@ -206,6 +194,22 @@ class Encyclopedia(callbacks.Plugin):
|
||||
if value.startswith('also '):
|
||||
name += '-also'
|
||||
value = value[5:].strip()
|
||||
if len(name) > 20:
|
||||
irc.error("I am only a bot, please don't think I'm intelligent :)")
|
||||
return
|
||||
if not capab(msg.prefix, 'editfactoids'):
|
||||
irc.reply("Your edit request has been forwarded to %s. Thank you for your attention to detail"%self.registryValue('relaychannel'),private=True)
|
||||
irc.queueMsg(ircmsgs.privmsg(self.registryValue('relaychannel'), "In %s, %s said: %s" % (msg.args[0], msg.nick, msg.args[1])))
|
||||
lfd = open(logdir + '/botlogs/lock','a')
|
||||
fcntl.lockf(lfd, fcntl.LOCK_EX)
|
||||
fd = open(logdir + '/botlogs/%s.log' % datetime.date.today().strftime('%Y-%m-%d'),'a')
|
||||
fd.write("%s %-20s %-16s %s\n" % (datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S'), channel, msg.nick, msg.args[1]))
|
||||
fd.close()
|
||||
fcntl.lockf(lfd,fcntl.LOCK_UN)
|
||||
lfd.close()
|
||||
os.chmod(logdir + '/botlogs/%s.log' % datetime.date.today().strftime('%Y-%m-%d'),0644)
|
||||
return
|
||||
# All clear!
|
||||
#irc.reply(str((name, value)))
|
||||
####
|
||||
# Find existing factoid
|
||||
@ -281,6 +285,7 @@ class Encyclopedia(callbacks.Plugin):
|
||||
irc.error("Unresolvable alias: %s" % alias)
|
||||
return
|
||||
# Finally, save
|
||||
log("(%s) UPDATE facts SET value = %s WHERE name = %s" % (msg.prefix, f.value, f.name))
|
||||
cur.execute("UPDATE facts SET value = %s WHERE name = %s", (f.value, f.name))
|
||||
db.commit()
|
||||
irc.reply("I'll remember that, %s" % msg.nick)
|
||||
@ -339,8 +344,14 @@ class Encyclopedia(callbacks.Plugin):
|
||||
if not i.startswith('Package'):
|
||||
queue(irc, target, i)
|
||||
else:
|
||||
if len(text) > 16:
|
||||
irc.error("I am only a bot, please don't think I'm intelligent :)")
|
||||
return
|
||||
irc.reply(self.registryValue('notfoundmsg') % text)
|
||||
else:
|
||||
if len(text) > 16:
|
||||
irc.error("I am only a bot, please don't think I'm intelligent :)")
|
||||
return
|
||||
irc.reply(self.registryValue('notfoundmsg') % text)
|
||||
for key in ('channel_secondary', 'global_secondary'):
|
||||
if getattr(factoids, key):
|
||||
@ -364,6 +375,8 @@ def send(irc, to, msg):
|
||||
def addressed(recipients, text, irc):
|
||||
if recipients[0] == '#':
|
||||
text = text.strip()
|
||||
if text.lower() == '!ubotu':
|
||||
return 'ubotu'
|
||||
if text[0] == '!':
|
||||
text = text[1:]
|
||||
if text.lower().startswith('ubotu') and (len(text) < 5 or not text[5].isalnum()):
|
||||
@ -395,10 +408,10 @@ aptcommand = """apt-cache\\
|
||||
%%s %%s""" % tuple([aptdir]*4)
|
||||
aptfilecommand = """apt-file -s %s/%%s.list -c %s/apt-file/%%s -l -F search %%s""" % tuple([aptdir]*2)
|
||||
def findpkg(pkg,checkdists,filelookup=True):
|
||||
_pkg = ''.join([x for x in pkg.strip().split(None,1)[0] if x.isalnum or x in '.-_'])
|
||||
_pkg = ''.join([x for x in pkg.strip().split(None,1)[0] if x.isalnum or x in '.-_+'])
|
||||
distro = checkdists[0]
|
||||
if len(pkg.strip().split()) > 1:
|
||||
distro = ''.join([x for x in pkg.strip().split(None,2)[1] if x.isalnum or x in '.-_'])
|
||||
distro = ''.join([x for x in pkg.strip().split(None,2)[1] if x.isalnum or x in '.-_+'])
|
||||
if distro not in distros:
|
||||
distro = checkdists[0]
|
||||
pkg = _pkg
|
||||
@ -420,10 +433,10 @@ def findpkg(pkg,checkdists,filelookup=True):
|
||||
return "Found: %s" % ', '.join(pkgs[:5])
|
||||
|
||||
def pkginfo(pkg,checkdists):
|
||||
_pkg = ''.join([x for x in pkg.strip().split(None,1)[0] if x.isalnum() or x in '.-_'])
|
||||
_pkg = ''.join([x for x in pkg.strip().split(None,1)[0] if x.isalnum() or x in '.-_+'])
|
||||
distro = None
|
||||
if len(pkg.strip().split()) > 1:
|
||||
distro = ''.join([x for x in pkg.strip().split(None,2)[1] if x.isalnum() or x in '-._'])
|
||||
distro = ''.join([x for x in pkg.strip().split(None,2)[1] if x.isalnum() or x in '-._+'])
|
||||
if distro:
|
||||
if distro not in distros:
|
||||
checkdists = [checkdists[0]]
|
||||
@ -554,4 +567,8 @@ def capab(prefix, capability):
|
||||
except:
|
||||
pass
|
||||
return False
|
||||
def log(msg):
|
||||
fd = open('/home/dennis/editlog','a')
|
||||
fd.write('%s\n' % msg)
|
||||
fd.close()
|
||||
Class = Encyclopedia
|
||||
|
Reference in New Issue
Block a user