diff --git a/plugins/Sourceforge.py b/plugins/Sourceforge.py
index c51ce8a10..a31729aaf 100644
--- a/plugins/Sourceforge.py
+++ b/plugins/Sourceforge.py
@@ -96,11 +96,6 @@ conf.registerChannelValue(conf.supybot.plugins.Sourceforge, 'trackerSnarfer',
conf.registerChannelValue(conf.supybot.plugins.Sourceforge, 'defaultProject',
registry.String('', """Sets the default project to use in the case that no
explicit project is given."""))
-#conf.registerGlobalValue(conf.supybot.plugins.Sourceforge,
-# 'enableSeparateTrackersCommands',
-# registry.Boolean(True, """Determines whether the bot will recognize the
-# tracker types as commands. For example, "@bugs supybot" would be the same
-# as calling "@trackers bugs supybot"."""))
class Sourceforge(callbacks.PrivmsgCommandAndRegexp):
"""
@@ -112,7 +107,7 @@ class Sourceforge(callbacks.PrivmsgCommandAndRegexp):
_reopts = re.I
_infoRe = re.compile(r'
(\d+) | ([^<]+)', _reopts)
+ r'"([^"]+)">([^<]+)', re.I)
_hrefOpts = '&set=custom&_assigned_to=0&_status=%s&_category=100' \
'&_group=100&order=artifact_id&sort=DESC'
_resolution=re.compile(r'(Resolution): (.+?) | ',_reopts)
@@ -132,20 +127,10 @@ class Sourceforge(callbacks.PrivmsgCommandAndRegexp):
super(Sourceforge, self).__init__()
self.__class__.sf = self.__class__.sourceforge
-# def isCommand(self, methodName):
-# if hasattr(self, methodName):
-# return True
-# if methodName not in ('bugs', 'rfes', 'patches'):
-# return False
-# elif self.registryValue('enableSeparateTrackersCommands'):
-# return True
-# else:
-# return False
-
def _formatResp(self, text, num=''):
"""
Parses the Sourceforge query to return a list of tuples that
- contain the bug/rfe information.
+ contain the tracker information.
"""
if num:
for item in ifilter(lambda s, n=num: s and n in s,
@@ -157,6 +142,9 @@ class Sourceforge(callbacks.PrivmsgCommandAndRegexp):
yield (item[0], utils.htmlToText(item[2]))
def _getTrackerURL(self, project, regex, status):
+ """
+ Searches the project's Summary page to find the proper tracker link.
+ """
try:
text = webutils.getUrl('%s%s' % (self._projectURL, project))
m = regex.search(text)
@@ -169,6 +157,9 @@ class Sourceforge(callbacks.PrivmsgCommandAndRegexp):
raise callbacks.Error, str(e)
def _getTrackerList(self, url):
+ """
+ Searches the tracker list page and returns a list of the trackers.
+ """
try:
text = webutils.getUrl(url)
if "No matches found." in text:
@@ -188,6 +179,9 @@ class Sourceforge(callbacks.PrivmsgCommandAndRegexp):
_sfTitle = re.compile(r'Detail:(\d+) - ([^<]+)', re.I)
_linkType = re.compile(r'(\w+ \w+|\w+): Tracker Detailed View', re.I)
def _getTrackerInfo(self, url):
+ """
+ Parses the specific tracker page, returning useful information.
+ """
try:
s = webutils.getUrl(url)
resp = []
@@ -231,33 +225,22 @@ class Sourceforge(callbacks.PrivmsgCommandAndRegexp):
'rfes': re.compile(r'"([^"]+)">RFE'),
'patches': re.compile(r'"([^"]+)">Patches'),
}
- def trackers(self, irc, msg, args):
- """[--{any,open,closed,deleted,pending}] {bugs,patches,rfes}
- []
-
- Returns a list of the most recent trackers filed against .
- is not needed if there is a default project set. Search
- defaults to open trackers.
- """
+ def _trackers(self, irc, args, msg, tracker):
(optlist, rest) = getopt.getopt(args, '', self._statusOpt.keys())
- (tracker, project) = privmsgs.getArgs(rest, optional=1)
+ project = privmsgs.getArgs(rest, required=0, optional=1)
status = 'open'
for (option, _) in optlist:
option = option.lstrip('-').lower()
if option in self._statusOpt:
status = option
try:
- int(tracker)
- # They want the tracker command, they're giving us an id#.
- s = 'Use the tracker command (e.g., tracker %s) for info about a'\
- ' specific tracker.' % tracker
+ int(project)
+ s = 'Use the tracker command to get information about a specific'\
+ 'tracker.'
irc.error(s)
return
except ValueError:
pass
- tracker = tracker.lower()
- if tracker not in self._trackerLink:
- raise callbacks.ArgumentError
if not project:
project = self.registryValue('defaultProject', msg.args[0])
if not project:
@@ -271,6 +254,33 @@ class Sourceforge(callbacks.PrivmsgCommandAndRegexp):
return
irc.reply(self._getTrackerList(url))
+ def bugs(self, irc, msg, args):
+ """[--{any,open,closed,deleted,pending}] []
+
+ Returns a list of the most recent bugs filed against .
+ is not needed if there is a default project set. Search
+ defaults to open bugs.
+ """
+ self._trackers(irc, args, msg, 'bugs')
+
+ def rfes(self, irc, msg, args):
+ """[--{any,open,closed,deleted,pending}] []
+
+ Returns a list of the most recent rfes filed against .
+ is not needed if there is a default project set. Search
+ defaults to open rfes.
+ """
+ self._trackers(irc, args, msg, 'rfes')
+
+ def patches(self, irc, msg, args):
+ """[--{any,open,closed,deleted,pending}] []
+
+ Returns a list of the most recent patches filed against .
+ is not needed if there is a default project set. Search
+ defaults to open patches.
+ """
+ self._trackers(irc, args, msg, 'patches')
+
_totbugs = re.compile(r'Bugs\s+?\( ([^<]+)', re.S | re.I)
def _getNumBugs(self, project):
text = webutils.getUrl('%s%s' % (self._projectURL, project))
@@ -291,7 +301,7 @@ class Sourceforge(callbacks.PrivmsgCommandAndRegexp):
return ''
def total(self, irc, msg, args):
- """[bugs|rfes] []
+ """{bugs,rfes} []
Returns the total count of open bugs or rfes. is only
necessary if a default project is not set.
diff --git a/test/test_Sourceforge.py b/test/test_Sourceforge.py
index 35aafd615..0fbe19b45 100644
--- a/test/test_Sourceforge.py
+++ b/test/test_Sourceforge.py
@@ -40,54 +40,54 @@ class SourceforgeTest(ChannelPluginTestCase):
plugins = ('Sourceforge',)
if network:
def testAny(self):
- m = self.getMsg('trackers --any bugs gaim')
+ m = self.getMsg('bugs --any gaim')
self.failUnless(m, 'No response from Sourceforge.')
n = re.search('#(\d+)', m.args[1]).group(1)
self.assertNotError('tracker %s' % n)
- m = self.getMsg('trackers --any rfes gaim')
+ m = self.getMsg('rfes --any gaim')
self.failUnless(m, 'No response from Sourceforge.')
n = re.search('#(\d+)', m.args[1]).group(1)
self.assertNotError('tracker %s' % n)
def testClosed(self):
- m = self.getMsg('trackers --closed bugs gaim')
+ m = self.getMsg('bugs --closed gaim')
self.failUnless(m, 'No response from Sourceforge.')
n = re.search('#(\d+)', m.args[1]).group(1)
self.assertNotError('tracker %s' % n)
- m = self.getMsg('trackers --closed patches gaim')
+ m = self.getMsg('patches --closed gaim')
self.failUnless(m, 'No response from Sourceforge.')
n = re.search('#(\d+)', m.args[1]).group(1)
self.assertNotError('tracker %s' % n)
def testDeleted(self):
- m = self.getMsg('trackers --deleted bugs gaim')
+ m = self.getMsg('bugs --deleted gaim')
self.failUnless(m, 'No response from Sourceforge.')
n = re.search('#(\d+)', m.args[1]).group(1)
self.assertNotError('tracker %s' % n)
- m = self.getMsg('trackers --deleted rfes gaim')
+ m = self.getMsg('rfes --deleted gaim')
self.failUnless(m, 'No response from Sourceforge.')
n = re.search('#(\d+)', m.args[1]).group(1)
self.assertNotError('tracker %s' % n)
def testOpen(self):
- m = self.getMsg('trackers --open bugs gaim')
+ m = self.getMsg('bugs --open gaim')
self.failUnless(m, 'No response from Sourceforge.')
n = re.search('#(\d+)', m.args[1]).group(1)
self.assertNotError('tracker %s' % n)
- m = self.getMsg('trackers --open rfes gaim')
+ m = self.getMsg('rfes --open gaim')
self.failUnless(m, 'No response from Sourceforge.')
n = re.search('#(\d+)', m.args[1]).group(1)
self.assertNotError('tracker %s' % n)
def testTrackers(self):
- self.assertHelp('trackers bugs')
- self.assertRegexp('trackers bugs 83423', 'find the Bug')
+ self.assertHelp('bugs')
+ self.assertRegexp('bugs 83423', 'use the tracker')
try:
original = Sf.defaultProject()
Sf.defaultProject.set('supybot')
- self.assertRegexp('trackers bugs alkjfi83fa8', 'find the Bugs')
- self.assertNotError('trackers rfes gaim')
- self.assertNotError('trackers patches')
+ self.assertRegexp('bugs alkjfi83fa8', 'find the Bugs')
+ self.assertNotError('rfes gaim')
+ self.assertNotError('patches')
finally:
Sf.defaultProject.set(original)
@@ -95,9 +95,9 @@ class SourceforgeTest(ChannelPluginTestCase):
try:
original = Sf.defaultProject()
Sf.defaultProject.setValue('supybot')
- self.assertNotError('trackers bugs')
+ self.assertNotError('bugs')
Sf.defaultProject.setValue('')
- self.assertHelp('trackers bugs')
+ self.assertHelp('bugs')
finally:
Sf.defaultProject.set(original)