mirror of https://github.com/Mikaela/Limnoria.git
Merge remote-tracking branch 'progval/testing' into testing
This commit is contained in:
commit
9477ba20fb
|
@ -34,7 +34,7 @@ import supybot.conf as conf
|
||||||
|
|
||||||
class ConfigTestCase(ChannelPluginTestCase):
|
class ConfigTestCase(ChannelPluginTestCase):
|
||||||
# We add utilities so there's something in supybot.plugins.
|
# We add utilities so there's something in supybot.plugins.
|
||||||
plugins = ('Config', 'Utilities', 'AutoMode')
|
plugins = ('Config', 'Utilities')
|
||||||
def testGet(self):
|
def testGet(self):
|
||||||
self.assertNotRegexp('config get supybot.reply', r'registry\.Group')
|
self.assertNotRegexp('config get supybot.reply', r'registry\.Group')
|
||||||
self.assertResponse('config supybot.protocols.irc.throttleTime', '0.0')
|
self.assertResponse('config supybot.protocols.irc.throttleTime', '0.0')
|
||||||
|
@ -49,9 +49,6 @@ class ConfigTestCase(ChannelPluginTestCase):
|
||||||
def testHelp(self):
|
def testHelp(self):
|
||||||
self.assertError('config help alsdkfj')
|
self.assertError('config help alsdkfj')
|
||||||
self.assertError('config help supybot.alsdkfj')
|
self.assertError('config help supybot.alsdkfj')
|
||||||
self.assertNotRegexp('config list supybot', '.*alsdkfj.*')
|
|
||||||
self.assertError('config help supybot.plugins.AutoMode.ban.alsdkfj')
|
|
||||||
self.assertNotRegexp('config list supybot.plugins.AutoMode.ban', '.*alsdkfj.*')
|
|
||||||
self.assertNotError('config help supybot') # We tell the user to list.
|
self.assertNotError('config help supybot') # We tell the user to list.
|
||||||
self.assertNotError('config help supybot.plugins')
|
self.assertNotError('config help supybot.plugins')
|
||||||
self.assertNotError('config help supybot.replies.success')
|
self.assertNotError('config help supybot.replies.success')
|
||||||
|
|
|
@ -2,7 +2,7 @@ msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: Supybot-fr\n"
|
"Project-Id-Version: Supybot-fr\n"
|
||||||
"POT-Creation-Date: 2011-02-26 09:49+CET\n"
|
"POT-Creation-Date: 2011-02-26 09:49+CET\n"
|
||||||
"PO-Revision-Date: 2011-06-26 18:57+0200\n"
|
"PO-Revision-Date: 2011-08-10 14:27+0200\n"
|
||||||
"Last-Translator: skizzhg <skizzhg@gmx.com>\n"
|
"Last-Translator: skizzhg <skizzhg@gmx.com>\n"
|
||||||
"Language-Team: Italian <skizzhg@gmx.com>\n"
|
"Language-Team: Italian <skizzhg@gmx.com>\n"
|
||||||
"Language: it\n"
|
"Language: it\n"
|
||||||
|
@ -159,7 +159,28 @@ msgstr ""
|
||||||
msgid "There were no notes for %r"
|
msgid "There were no notes for %r"
|
||||||
msgstr "Non ci sono note per %r"
|
msgstr "Non ci sono note per %r"
|
||||||
|
|
||||||
#: plugin.py:231
|
#: plugin.py:212
|
||||||
|
#, docstring
|
||||||
|
msgid ""
|
||||||
|
"<nick>\n"
|
||||||
|
"\n"
|
||||||
|
" Removes the latest note you sent to <nick>.\n"
|
||||||
|
" "
|
||||||
|
msgstr ""
|
||||||
|
"<nick>\n"
|
||||||
|
"\n"
|
||||||
|
" Rimuove l'ultima nota inviata a <nick>.\n"
|
||||||
|
" "
|
||||||
|
|
||||||
|
#: plugin.py:217
|
||||||
|
msgid "There are no note waiting for %s."
|
||||||
|
msgstr "Non ci sono note in attesa per %s."
|
||||||
|
|
||||||
|
#: plugin.py:228
|
||||||
|
msgid "There are no note from you waiting for %s."
|
||||||
|
msgstr "Non ci sono note in attesa per %s da te inviate."
|
||||||
|
|
||||||
|
#: plugin.py:252
|
||||||
msgid "Sent %s: <%s> %s"
|
msgid "Sent %s: <%s> %s"
|
||||||
msgstr "Inviata %s: <%s> %s"
|
msgstr "Inviata %s: <%s> %s"
|
||||||
|
|
||||||
|
|
|
@ -2,7 +2,7 @@ msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: Supybot-fr\n"
|
"Project-Id-Version: Supybot-fr\n"
|
||||||
"POT-Creation-Date: 2011-02-26 09:49+CET\n"
|
"POT-Creation-Date: 2011-02-26 09:49+CET\n"
|
||||||
"PO-Revision-Date: 2011-08-10 02:11+0200\n"
|
"PO-Revision-Date: 2011-08-10 14:39+0200\n"
|
||||||
"Last-Translator: skizzhg <skizzhg@gmx.com>\n"
|
"Last-Translator: skizzhg <skizzhg@gmx.com>\n"
|
||||||
"Language-Team: Italian <skizzhg@gmx.com>\n"
|
"Language-Team: Italian <skizzhg@gmx.com>\n"
|
||||||
"Language: it\n"
|
"Language: it\n"
|
||||||
|
@ -161,12 +161,12 @@ msgstr "La versione di questo Supybot è %s. %s"
|
||||||
msgid ""
|
msgid ""
|
||||||
"takes no arguments\n"
|
"takes no arguments\n"
|
||||||
"\n"
|
"\n"
|
||||||
" Returns a URL saying where to get Supybot.\n"
|
" Returns a URL saying where to get Limnoria.\n"
|
||||||
" "
|
" "
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"non necessita argomenti\n"
|
"non necessita argomenti\n"
|
||||||
"\n"
|
"\n"
|
||||||
" Riporta un URL che dice dove ottenere Supybot.\n"
|
" Riporta un URL che dice dove ottenere Limnoria.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:243
|
#: plugin.py:243
|
||||||
|
@ -274,7 +274,7 @@ msgstr "Non ho mai visto %s, lascio a te l'invio del messaggio."
|
||||||
msgid "%s wants me to tell you: %s"
|
msgid "%s wants me to tell you: %s"
|
||||||
msgstr "%s vuole che ti dica: %s"
|
msgstr "%s vuole che ti dica: %s"
|
||||||
|
|
||||||
#: plugin.py:430
|
#: plugin.py:431
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"takes no arguments\n"
|
"takes no arguments\n"
|
||||||
|
@ -287,7 +287,7 @@ msgstr ""
|
||||||
" Controlla che il bot sia ancora vivo.\n"
|
" Controlla che il bot sia ancora vivo.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:434
|
#: plugin.py:435
|
||||||
msgid "pong"
|
msgid "pong"
|
||||||
msgstr "pong"
|
msgstr "pong"
|
||||||
|
|
||||||
|
|
|
@ -43,10 +43,15 @@ import supybot.irclib as irclib
|
||||||
import supybot.ircmsgs as ircmsgs
|
import supybot.ircmsgs as ircmsgs
|
||||||
import supybot.ircutils as ircutils
|
import supybot.ircutils as ircutils
|
||||||
import supybot.callbacks as callbacks
|
import supybot.callbacks as callbacks
|
||||||
|
from supybot import commands
|
||||||
|
|
||||||
from supybot.utils.iter import ifilter
|
from supybot.utils.iter import ifilter
|
||||||
from supybot.i18n import PluginInternationalization, internationalizeDocstring
|
from supybot.i18n import PluginInternationalization, internationalizeDocstring
|
||||||
_ = PluginInternationalization('Misc')
|
_ = PluginInternationalization('Misc')
|
||||||
|
|
||||||
|
class RegexpTimeout(Exception):
|
||||||
|
pass
|
||||||
|
|
||||||
class Misc(callbacks.Plugin):
|
class Misc(callbacks.Plugin):
|
||||||
def __init__(self, irc):
|
def __init__(self, irc):
|
||||||
self.__parent = super(Misc, self)
|
self.__parent = super(Misc, self)
|
||||||
|
@ -332,10 +337,27 @@ class Misc(callbacks.Plugin):
|
||||||
predicates.setdefault('without', []).append(f)
|
predicates.setdefault('without', []).append(f)
|
||||||
elif option == 'regexp':
|
elif option == 'regexp':
|
||||||
def f(m, arg=arg):
|
def f(m, arg=arg):
|
||||||
|
def f1(s, arg):
|
||||||
|
"""Since we can't enqueue match objects into the multiprocessing queue,
|
||||||
|
we'll just wrap the function to return bools."""
|
||||||
|
if arg.search(s) is not None:
|
||||||
|
return True
|
||||||
|
else:
|
||||||
|
return False
|
||||||
if ircmsgs.isAction(m):
|
if ircmsgs.isAction(m):
|
||||||
return arg.search(ircmsgs.unAction(m))
|
m1 = ircmsgs.unAction(m)
|
||||||
|
#return arg.search(ircmsgs.unAction(m))
|
||||||
else:
|
else:
|
||||||
return arg.search(m.args[1])
|
m1 = m.args[1]
|
||||||
|
#return arg.search(m.args[1])
|
||||||
|
try:
|
||||||
|
# use a subprocess here, since specially crafted regexps can
|
||||||
|
# take exponential time and hang up the bot.
|
||||||
|
# timeout of 0.1 should be more than enough for any normal regexp.
|
||||||
|
v = commands.process(f1, m1, arg, timeout=0.1, pn=self.name(), cn='last')
|
||||||
|
return v
|
||||||
|
except commands.ProcessTimeoutError:
|
||||||
|
return False
|
||||||
predicates.setdefault('regexp', []).append(f)
|
predicates.setdefault('regexp', []).append(f)
|
||||||
elif option == 'nolimit':
|
elif option == 'nolimit':
|
||||||
nolimit = True
|
nolimit = True
|
||||||
|
@ -370,8 +392,12 @@ class Misc(callbacks.Plugin):
|
||||||
showNick = True
|
showNick = True
|
||||||
for m in iterable:
|
for m in iterable:
|
||||||
for predicate in predicates:
|
for predicate in predicates:
|
||||||
if not predicate(m):
|
try:
|
||||||
break
|
if not predicate(m):
|
||||||
|
break
|
||||||
|
except RegexpTimeout:
|
||||||
|
irc.error(_('The regular expression timed out.'))
|
||||||
|
return
|
||||||
else:
|
else:
|
||||||
if nolimit:
|
if nolimit:
|
||||||
resp.append(ircmsgs.prettyPrint(m,
|
resp.append(ircmsgs.prettyPrint(m,
|
||||||
|
|
|
@ -42,6 +42,7 @@ import supybot.ircmsgs as ircmsgs
|
||||||
import supybot.plugins as plugins
|
import supybot.plugins as plugins
|
||||||
import supybot.ircutils as ircutils
|
import supybot.ircutils as ircutils
|
||||||
import supybot.callbacks as callbacks
|
import supybot.callbacks as callbacks
|
||||||
|
from supybot import commands
|
||||||
from supybot.i18n import PluginInternationalization, internationalizeDocstring
|
from supybot.i18n import PluginInternationalization, internationalizeDocstring
|
||||||
_ = PluginInternationalization('Note')
|
_ = PluginInternationalization('Note')
|
||||||
|
|
||||||
|
@ -294,7 +295,8 @@ class Note(callbacks.Plugin):
|
||||||
own = to
|
own = to
|
||||||
for (option, arg) in optlist:
|
for (option, arg) in optlist:
|
||||||
if option == 'regexp':
|
if option == 'regexp':
|
||||||
criteria.append(arg.search)
|
criteria.append(lambda x: commands.regexp_wrapper(x, reobj=arg,
|
||||||
|
timeout=0.1, plugin_name = self.name(), fcn_name='search'))
|
||||||
elif option == 'sent':
|
elif option == 'sent':
|
||||||
own = frm
|
own = frm
|
||||||
if glob:
|
if glob:
|
||||||
|
|
|
@ -2,7 +2,7 @@ msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: Supybot-fr\n"
|
"Project-Id-Version: Supybot-fr\n"
|
||||||
"POT-Creation-Date: 2011-02-26 09:49+CET\n"
|
"POT-Creation-Date: 2011-02-26 09:49+CET\n"
|
||||||
"PO-Revision-Date: 2011-08-10 02:27+0200\n"
|
"PO-Revision-Date: 2011-08-10 14:43+0200\n"
|
||||||
"Last-Translator: skizzhg <skizzhg@gmx.com>\n"
|
"Last-Translator: skizzhg <skizzhg@gmx.com>\n"
|
||||||
"Language-Team: Italian <skizzhg@gmx.com>\n"
|
"Language-Team: Italian <skizzhg@gmx.com>\n"
|
||||||
"Language: it\n"
|
"Language: it\n"
|
||||||
|
@ -10,47 +10,48 @@ msgstr ""
|
||||||
"Content-Type: text/plain; charset=UTF-8\n"
|
"Content-Type: text/plain; charset=UTF-8\n"
|
||||||
"Content-Transfer-Encoding: 8bit\n"
|
"Content-Transfer-Encoding: 8bit\n"
|
||||||
|
|
||||||
#: plugin.py:203 plugin.py:284
|
#: plugin.py:204 plugin.py:285
|
||||||
msgid "%s was last seen in %s %s ago: %s"
|
msgid "%s was last seen in %s %s ago: %s"
|
||||||
msgstr "%s è stato visto per l'ultima volta in %s %s fa: %s"
|
msgstr "%s è stato visto per l'ultima volta in %s %s fa: %s"
|
||||||
|
|
||||||
#: plugin.py:210
|
#: plugin.py:211
|
||||||
msgid "%s (%s ago)"
|
msgid "%s (%s ago)"
|
||||||
msgstr "%s (%s fa)"
|
msgstr "%s (%s fa)"
|
||||||
|
|
||||||
#: plugin.py:212
|
#: plugin.py:213
|
||||||
msgid "%s could be %L"
|
msgid "%s could be %L"
|
||||||
msgstr "%s potrebbe essere %L"
|
msgstr "%s potrebbe essere %L"
|
||||||
|
|
||||||
#: plugin.py:212
|
#: plugin.py:213
|
||||||
msgid "or"
|
msgid "or"
|
||||||
msgstr "oppure"
|
msgstr "oppure"
|
||||||
|
|
||||||
#: plugin.py:214
|
#: plugin.py:215
|
||||||
msgid "I haven't seen anyone matching %s."
|
msgid "I haven't seen anyone matching %s."
|
||||||
msgstr "Non ho visto nessuno che corrisponda a %s."
|
msgstr "Non ho visto nessuno che corrisponda a %s."
|
||||||
|
|
||||||
#: plugin.py:216 plugin.py:288
|
#: plugin.py:217 plugin.py:289
|
||||||
msgid "I have not seen %s."
|
msgid "I have not seen %s."
|
||||||
msgstr "Non ho visto %s."
|
msgstr "Non ho visto %s."
|
||||||
|
|
||||||
#: plugin.py:220
|
#: plugin.py:221
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"[<channel>] <nick>\n"
|
"[<channel>] <nick>\n"
|
||||||
"\n"
|
"\n"
|
||||||
" Returns the last time <nick> was seen and what <nick> was last seen\n"
|
" Returns the last time <nick> was seen and what <nick> was last seen\n"
|
||||||
" saying. <channel> is only necessary if the message isn't sent on the\n"
|
" saying. <channel> is only necessary if the message isn't sent on the\n"
|
||||||
" channel itself.\n"
|
" channel itself. <nick> may contain * as a wildcard.\n"
|
||||||
" "
|
" "
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"[<canale>] <nick>\n"
|
"[<canale>] <nick>\n"
|
||||||
"\n"
|
"\n"
|
||||||
" Riporta l'ultima volta che <nick> è stato visto e cosa stava dicendo.\n"
|
" Riporta l'ultima volta che <nick> è stato visto e cosa stava dicendo.\n"
|
||||||
" <canale> è necessario solo se il messaggio non viene inviato nel canale stesso.\n"
|
" <canale> è necessario solo se il messaggio non viene inviato nel canale\n"
|
||||||
|
" stesso. <nick> può contenere * come wildcard.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:231
|
#: plugin.py:232
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"[<channel>] [--user <name>] [<nick>]\n"
|
"[<channel>] [--user <name>] [<nick>]\n"
|
||||||
|
@ -73,15 +74,15 @@ msgstr ""
|
||||||
" solo se il messaggio non viene inviato nel canale stesso.\n"
|
" solo se il messaggio non viene inviato nel canale stesso.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:261
|
#: plugin.py:262
|
||||||
msgid "Someone was last seen in %s %s ago: %s"
|
msgid "Someone was last seen in %s %s ago: %s"
|
||||||
msgstr "Qualcuno è stato visto per l'ultima volta in %s %s fa: %s"
|
msgstr "Qualcuno è stato visto per l'ultima volta in %s %s fa: %s"
|
||||||
|
|
||||||
#: plugin.py:265
|
#: plugin.py:266
|
||||||
msgid "I have never seen anyone."
|
msgid "I have never seen anyone."
|
||||||
msgstr "Non ho mai visto nessuno."
|
msgstr "Non ho mai visto nessuno."
|
||||||
|
|
||||||
#: plugin.py:269
|
#: plugin.py:270
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"[<channel>]\n"
|
"[<channel>]\n"
|
||||||
|
@ -96,15 +97,15 @@ msgstr ""
|
||||||
" solo se il messaggio non viene inviato nel canale stesso.\n"
|
" solo se il messaggio non viene inviato nel canale stesso.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:292
|
#: plugin.py:293
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"[<canale>] <name>\n"
|
"[<channel>] <name>\n"
|
||||||
"\n"
|
"\n"
|
||||||
" Returns the last time <name> was seen and what <name> was last seen\n"
|
" Returns the last time <name> was seen and what <name> was last seen\n"
|
||||||
" saying. This looks up <name> in the user seen database, which means\n"
|
" saying. This looks up <name> in the user seen database, which means\n"
|
||||||
" that it could be any nick recognized as user <name> that was seen.\n"
|
" that it could be any nick recognized as user <name> that was seen.\n"
|
||||||
" <canale> is only necessary if the message isn't sent in the channel\n"
|
" <channel> is only necessary if the message isn't sent in the channel\n"
|
||||||
" itself.\n"
|
" itself.\n"
|
||||||
" "
|
" "
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
@ -116,7 +117,7 @@ msgstr ""
|
||||||
" <canale> è necessario solo se il messaggio non viene inviato nel canale stesso.\n"
|
" <canale> è necessario solo se il messaggio non viene inviato nel canale stesso.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:305
|
#: plugin.py:306
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"[<channel>] <nick>\n"
|
"[<channel>] <nick>\n"
|
||||||
|
@ -129,15 +130,15 @@ msgstr ""
|
||||||
" Riporta i messaggi da quando <nick> ha lasciato il canale l'ultima volta.\n"
|
" Riporta i messaggi da quando <nick> ha lasciato il canale l'ultima volta.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:312
|
#: plugin.py:313
|
||||||
msgid "You must be in %s to use this command."
|
msgid "You must be in %s to use this command."
|
||||||
msgstr "Per usare questo comando bisogna essere in %s."
|
msgstr "Per usare questo comando bisogna essere in %s."
|
||||||
|
|
||||||
#: plugin.py:333
|
#: plugin.py:334
|
||||||
msgid "I couldn't find in my history of %s messages where %r last left the %s"
|
msgid "I couldn't find in my history of %s messages where %r last left the %s"
|
||||||
msgstr "Non trovo nella cronologia dei messaggi di %s dove %r ha lasciato %s l'ultima volta."
|
msgstr "Non trovo nella cronologia dei messaggi di %s dove %r ha lasciato %s l'ultima volta."
|
||||||
|
|
||||||
#: plugin.py:342
|
#: plugin.py:343
|
||||||
msgid "Either %s didn't leave, or no messages were sent while %s was gone."
|
msgid "Either %s didn't leave, or no messages were sent while %s was gone."
|
||||||
msgstr "%s non è uscito o non ha inviato alcun messaggio quando se n'é andato."
|
msgstr "%s non è uscito o non ha inviato alcun messaggio quando se n'é andato."
|
||||||
|
|
||||||
|
|
|
@ -53,4 +53,11 @@ conf.registerGlobalValue(String.levenshtein, 'max',
|
||||||
this variable, to limit the size of arguments passed to the levenshtein
|
this variable, to limit the size of arguments passed to the levenshtein
|
||||||
command.""")))
|
command.""")))
|
||||||
|
|
||||||
|
conf.registerGroup(String, 're')
|
||||||
|
conf.registerGlobalValue(String.re, 'timeout',
|
||||||
|
registry.PositiveFloat(0.1, """Determines the maximum time, in seconds, that
|
||||||
|
a regular expression is given to execute before being terminated. Since
|
||||||
|
there is a possibility that user input for the re command can cause it to
|
||||||
|
eat up large amounts of ram or cpu time, it's a good idea to keep this
|
||||||
|
low. Most normal regexps should not take very long at all."""))
|
||||||
# vim:set shiftwidth=4 softtabstop=4 expandtab textwidth=79:
|
# vim:set shiftwidth=4 softtabstop=4 expandtab textwidth=79:
|
||||||
|
|
|
@ -146,10 +146,14 @@ class String(callbacks.Plugin):
|
||||||
s = _('You probably don\'t want to match the empty string.')
|
s = _('You probably don\'t want to match the empty string.')
|
||||||
irc.error(s)
|
irc.error(s)
|
||||||
else:
|
else:
|
||||||
irc.reply(f(text))
|
t = self.registryValue('re.timeout')
|
||||||
re = wrap(re, [('checkCapability', 'trusted'),
|
try:
|
||||||
first('regexpMatcher', 'regexpReplacer'),
|
v = commands.process(f, text, timeout=t, pn=self.name(), cn='re')
|
||||||
'text'])
|
irc.reply(v)
|
||||||
|
except commands.ProcessTimeoutError, e:
|
||||||
|
irc.error("ProcessTimeoutError: %s" % (e,))
|
||||||
|
re = thread(wrap(re, [first('regexpMatcher', 'regexpReplacer'),
|
||||||
|
'text']))
|
||||||
|
|
||||||
@internationalizeDocstring
|
@internationalizeDocstring
|
||||||
def xor(self, irc, msg, args, password, text):
|
def xor(self, irc, msg, args, password, text):
|
||||||
|
|
|
@ -171,8 +171,6 @@ class Time(callbacks.Plugin):
|
||||||
except ImportError:
|
except ImportError:
|
||||||
irc.error(_('Python-tz is required by the command, but is not '
|
irc.error(_('Python-tz is required by the command, but is not '
|
||||||
'installed on this computer.'))
|
'installed on this computer.'))
|
||||||
if len(timezone.split('/')) != 2:
|
|
||||||
irc.error(_('A timezone must be in the format region/city.'))
|
|
||||||
try:
|
try:
|
||||||
timezone = pytz.timezone(timezone)
|
timezone = pytz.timezone(timezone)
|
||||||
except pytz.UnknownTimeZoneError:
|
except pytz.UnknownTimeZoneError:
|
||||||
|
|
|
@ -2,7 +2,7 @@ msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: Supybot-fr\n"
|
"Project-Id-Version: Supybot-fr\n"
|
||||||
"POT-Creation-Date: 2011-02-26 09:49+CET\n"
|
"POT-Creation-Date: 2011-02-26 09:49+CET\n"
|
||||||
"PO-Revision-Date: 2011-08-10 02:33+0200\n"
|
"PO-Revision-Date: 2011-08-10 14:53+0200\n"
|
||||||
"Last-Translator: skizzhg <skizzhg@gmx.com>\n"
|
"Last-Translator: skizzhg <skizzhg@gmx.com>\n"
|
||||||
"Language-Team: Italian <skizzhg@gmx.com>\n"
|
"Language-Team: Italian <skizzhg@gmx.com>\n"
|
||||||
"Language: it\n"
|
"Language: it\n"
|
||||||
|
@ -10,6 +10,14 @@ msgstr ""
|
||||||
"Content-Type: text/plain; charset=UTF-8\n"
|
"Content-Type: text/plain; charset=UTF-8\n"
|
||||||
"Content-Transfer-Encoding: 8bit\n"
|
"Content-Transfer-Encoding: 8bit\n"
|
||||||
|
|
||||||
|
|
||||||
|
#: config.py:50
|
||||||
|
msgid ""
|
||||||
|
"Determines whether users can read the\n"
|
||||||
|
" todo-list of another user."
|
||||||
|
msgstr ""
|
||||||
|
"Determina se un utente possa leggere la lista delle cose da fare di un altro utente."
|
||||||
|
|
||||||
#: plugin.py:135
|
#: plugin.py:135
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
|
@ -27,43 +35,47 @@ msgstr ""
|
||||||
" ha aggiunto alla sua lista delle cose da fare.\n"
|
" ha aggiunto alla sua lista delle cose da fare.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:150
|
#: plugin.py:146
|
||||||
|
msgid "You are not allowed to see other users todo-list."
|
||||||
|
msgstr "Non hai l'autorizzazione pe rleggere la lista delle cose da fare degli altri utenti."
|
||||||
|
|
||||||
|
#: plugin.py:153
|
||||||
msgid "#%i: %s"
|
msgid "#%i: %s"
|
||||||
msgstr "#%i: %s"
|
msgstr "#%i: %s"
|
||||||
|
|
||||||
#: plugin.py:155
|
#: plugin.py:158
|
||||||
msgid "%s for %s: %L"
|
msgid "%s for %s: %L"
|
||||||
msgstr "%s per %s: %L"
|
msgstr "%s per %s: %L"
|
||||||
|
|
||||||
#: plugin.py:159
|
#: plugin.py:162
|
||||||
msgid "That user has no tasks in their todo list."
|
msgid "That user has no tasks in their todo list."
|
||||||
msgstr "Questo utente non ha compiti nella sua lista delle cose da fare."
|
msgstr "Questo utente non ha compiti nella sua lista delle cose da fare."
|
||||||
|
|
||||||
#: plugin.py:161
|
#: plugin.py:164
|
||||||
msgid "You have no tasks in your todo list."
|
msgid "You have no tasks in your todo list."
|
||||||
msgstr "Non hai compiti nella tua lista delle cose da fare."
|
msgstr "Non hai compiti nella tua lista delle cose da fare."
|
||||||
|
|
||||||
#: plugin.py:168
|
#: plugin.py:171
|
||||||
msgid "Active"
|
msgid "Active"
|
||||||
msgstr "Attivo"
|
msgstr "Attivo"
|
||||||
|
|
||||||
#: plugin.py:170
|
#: plugin.py:173
|
||||||
msgid "Inactive"
|
msgid "Inactive"
|
||||||
msgstr "Inattivo"
|
msgstr "Inattivo"
|
||||||
|
|
||||||
#: plugin.py:172
|
#: plugin.py:175
|
||||||
msgid ", priority: %i"
|
msgid ", priority: %i"
|
||||||
msgstr ", priorità: %i"
|
msgstr ", priorità: %i"
|
||||||
|
|
||||||
#: plugin.py:175
|
#: plugin.py:178
|
||||||
msgid "%s todo for %s: %s (Added at %s)"
|
msgid "%s todo for %s: %s (Added at %s)"
|
||||||
msgstr "%s compito per %s: %s (Aggiunto il %s)"
|
msgstr "%s compito per %s: %s (Aggiunto il %s)"
|
||||||
|
|
||||||
#: plugin.py:179 plugin.py:260 plugin.py:274
|
#: plugin.py:182 plugin.py:263 plugin.py:277
|
||||||
msgid "task id"
|
msgid "task id"
|
||||||
msgstr "id compito"
|
msgstr "id compito"
|
||||||
|
|
||||||
#: plugin.py:184
|
#: plugin.py:187
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"[--priority=<num>] <text>\n"
|
"[--priority=<num>] <text>\n"
|
||||||
|
@ -80,11 +92,11 @@ msgstr ""
|
||||||
" Ogni numero intero è valido.\n"
|
" Ogni numero intero è valido.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:195
|
#: plugin.py:198
|
||||||
msgid "(Todo #%i added)"
|
msgid "(Todo #%i added)"
|
||||||
msgstr "(Compito #%i aggiunto)"
|
msgstr "(Compito #%i aggiunto)"
|
||||||
|
|
||||||
#: plugin.py:201
|
#: plugin.py:204
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"<task id> [<task id> ...]\n"
|
"<task id> [<task id> ...]\n"
|
||||||
|
@ -97,15 +109,15 @@ msgstr ""
|
||||||
" Rimuove <id compito> dalla lista personale delle cose da fare.\n"
|
" Rimuove <id compito> dalla lista personale delle cose da fare.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:212
|
#: plugin.py:215
|
||||||
msgid "Task %i could not be removed either because that id doesn't exist or it has been removed already."
|
msgid "Task %i could not be removed either because that id doesn't exist or it has been removed already."
|
||||||
msgstr "Il compito %i non può essere rimosso in quanto l'id non esiste o è già stato rimosso."
|
msgstr "Il compito %i non può essere rimosso in quanto l'id non esiste o è già stato rimosso."
|
||||||
|
|
||||||
#: plugin.py:216
|
#: plugin.py:219
|
||||||
msgid "No tasks were removed because the following tasks could not be removed: %L."
|
msgid "No tasks were removed because the following tasks could not be removed: %L."
|
||||||
msgstr "Non è stato rimosso nessun compito perché i seguenti non possono essere rimossi: %L."
|
msgstr "Non è stato rimosso nessun compito perché i seguenti non possono essere rimossi: %L."
|
||||||
|
|
||||||
#: plugin.py:226
|
#: plugin.py:229
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"[--{regexp} <value>] [<glob> <glob> ...]\n"
|
"[--{regexp} <value>] [<glob> <glob> ...]\n"
|
||||||
|
@ -121,11 +133,11 @@ msgstr ""
|
||||||
" Se --regexp è fornita, il suo valore associato è usato come regexp e confrontato con i compiti.\n"
|
" Se --regexp è fornita, il suo valore associato è usato come regexp e confrontato con i compiti.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:246
|
#: plugin.py:249
|
||||||
msgid "No tasks matched that query."
|
msgid "No tasks matched that query."
|
||||||
msgstr "Nessun compito corrisponde alla richiesta."
|
msgstr "Nessun compito corrisponde alla richiesta."
|
||||||
|
|
||||||
#: plugin.py:252
|
#: plugin.py:255
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"<id> <priority>\n"
|
"<id> <priority>\n"
|
||||||
|
@ -138,7 +150,7 @@ msgstr ""
|
||||||
" Imposta la priorità del compito con l'id fornito al valore specificato.\n"
|
" Imposta la priorità del compito con l'id fornito al valore specificato.\n"
|
||||||
" "
|
" "
|
||||||
|
|
||||||
#: plugin.py:266
|
#: plugin.py:269
|
||||||
#, docstring
|
#, docstring
|
||||||
msgid ""
|
msgid ""
|
||||||
"<task id> <regexp>\n"
|
"<task id> <regexp>\n"
|
||||||
|
|
|
@ -41,6 +41,7 @@ from supybot.commands import *
|
||||||
import supybot.plugins as plugins
|
import supybot.plugins as plugins
|
||||||
import supybot.ircutils as ircutils
|
import supybot.ircutils as ircutils
|
||||||
import supybot.callbacks as callbacks
|
import supybot.callbacks as callbacks
|
||||||
|
from supybot import commands
|
||||||
from supybot.i18n import PluginInternationalization, internationalizeDocstring
|
from supybot.i18n import PluginInternationalization, internationalizeDocstring
|
||||||
_ = PluginInternationalization('Todo')
|
_ = PluginInternationalization('Todo')
|
||||||
|
|
||||||
|
@ -237,6 +238,8 @@ class Todo(callbacks.Plugin):
|
||||||
criteria = []
|
criteria = []
|
||||||
for (option, arg) in optlist:
|
for (option, arg) in optlist:
|
||||||
if option == 'regexp':
|
if option == 'regexp':
|
||||||
|
criteria.append(lambda x: commands.regexp_wrapper(x, reobj=arg,
|
||||||
|
timeout=0.1, plugin_name = self.name(), fcn_name='search'))
|
||||||
criteria.append(arg.search)
|
criteria.append(arg.search)
|
||||||
for glob in globs:
|
for glob in globs:
|
||||||
glob = utils.python.glob2re(glob)
|
glob = utils.python.glob2re(glob)
|
||||||
|
|
|
@ -50,6 +50,7 @@ import supybot.world as world
|
||||||
from supybot.commands import *
|
from supybot.commands import *
|
||||||
import supybot.ircutils as ircutils
|
import supybot.ircutils as ircutils
|
||||||
import supybot.callbacks as callbacks
|
import supybot.callbacks as callbacks
|
||||||
|
from supybot import commands
|
||||||
|
|
||||||
## i think we don't need any of this with sqlite3
|
## i think we don't need any of this with sqlite3
|
||||||
#try:
|
#try:
|
||||||
|
@ -431,7 +432,9 @@ class ChannelIdDatabasePlugin(callbacks.Plugin):
|
||||||
if opt == 'by':
|
if opt == 'by':
|
||||||
predicates.append(lambda r, arg=arg: r.by == arg.id)
|
predicates.append(lambda r, arg=arg: r.by == arg.id)
|
||||||
elif opt == 'regexp':
|
elif opt == 'regexp':
|
||||||
predicates.append(lambda r, arg=arg: arg.search(r.text))
|
predicates.append(lambda x: commands.regexp_wrapper(x.text, reobj=arg,
|
||||||
|
timeout=0.1, plugin_name = self.name(), fcn_name='search'))
|
||||||
|
#predicates.append(lambda r, arg=arg: arg.search(r.text))
|
||||||
if glob:
|
if glob:
|
||||||
def globP(r, glob=glob.lower()):
|
def globP(r, glob=glob.lower()):
|
||||||
return fnmatch.fnmatch(r.text.lower(), glob)
|
return fnmatch.fnmatch(r.text.lower(), glob)
|
||||||
|
|
|
@ -69,6 +69,61 @@ def thread(f):
|
||||||
f(self, irc, msg, args, *L, **kwargs)
|
f(self, irc, msg, args, *L, **kwargs)
|
||||||
return utils.python.changeFunctionName(newf, f.func_name, f.__doc__)
|
return utils.python.changeFunctionName(newf, f.func_name, f.__doc__)
|
||||||
|
|
||||||
|
class ProcessTimeoutError(Exception):
|
||||||
|
"""Gets raised when a process is killed due to timeout."""
|
||||||
|
pass
|
||||||
|
|
||||||
|
def process(f, *args, **kwargs):
|
||||||
|
"""Runs a function <f> in a subprocess.
|
||||||
|
|
||||||
|
Several extra keyword arguments can be supplied.
|
||||||
|
<pn>, the pluginname, and <cn>, the command name, are strings used to
|
||||||
|
create the process name, for identification purposes.
|
||||||
|
<timeout>, if supplied, limits the length of execution of target
|
||||||
|
function to <timeout> seconds."""
|
||||||
|
timeout = kwargs.pop('timeout', None)
|
||||||
|
|
||||||
|
q = multiprocessing.Queue()
|
||||||
|
def newf(f, q, *args, **kwargs):
|
||||||
|
try:
|
||||||
|
r = f(*args, **kwargs)
|
||||||
|
q.put(r)
|
||||||
|
except Exception as e:
|
||||||
|
q.put(e)
|
||||||
|
targetArgs = (f, q,) + args
|
||||||
|
p = callbacks.CommandProcess(target=newf,
|
||||||
|
args=targetArgs, kwargs=kwargs)
|
||||||
|
p.start()
|
||||||
|
p.join(timeout)
|
||||||
|
if p.is_alive():
|
||||||
|
p.terminate()
|
||||||
|
raise ProcessTimeoutError, "%s aborted due to timeout." % (p.name,)
|
||||||
|
try:
|
||||||
|
v = q.get(block=False)
|
||||||
|
except Queue.Empty:
|
||||||
|
v = "Nothing returned."
|
||||||
|
if isinstance(v, Exception):
|
||||||
|
v = "Error: " + str(v)
|
||||||
|
return v
|
||||||
|
|
||||||
|
def regexp_wrapper(s, reobj, timeout, plugin_name, fcn_name):
|
||||||
|
'''A convenient wrapper to stuff regexp search queries through a subprocess.
|
||||||
|
|
||||||
|
This is used because specially-crafted regexps can use exponential time
|
||||||
|
and hang the bot.'''
|
||||||
|
def re_bool(s, reobj):
|
||||||
|
"""Since we can't enqueue match objects into the multiprocessing queue,
|
||||||
|
we'll just wrap the function to return bools."""
|
||||||
|
if reobj.search(s) is not None:
|
||||||
|
return True
|
||||||
|
else:
|
||||||
|
return False
|
||||||
|
try:
|
||||||
|
v = process(re_bool, s, reobj, timeout=timeout, pn=plugin_name, cn=fcn_name)
|
||||||
|
return v
|
||||||
|
except ProcessTimeoutError:
|
||||||
|
return False
|
||||||
|
|
||||||
class UrlSnarfThread(world.SupyThread):
|
class UrlSnarfThread(world.SupyThread):
|
||||||
def __init__(self, *args, **kwargs):
|
def __init__(self, *args, **kwargs):
|
||||||
assert 'url' in kwargs
|
assert 'url' in kwargs
|
||||||
|
|
|
@ -206,7 +206,7 @@ class Group(object):
|
||||||
def __getattr__(self, attr):
|
def __getattr__(self, attr):
|
||||||
if attr in self._children:
|
if attr in self._children:
|
||||||
return self._children[attr]
|
return self._children[attr]
|
||||||
elif self._supplyDefault and attr.startswith('#'):
|
elif self._supplyDefault:
|
||||||
return self.__makeChild(attr, str(self))
|
return self.__makeChild(attr, str(self))
|
||||||
else:
|
else:
|
||||||
self.__nonExistentEntry(attr)
|
self.__nonExistentEntry(attr)
|
||||||
|
|
|
@ -1,3 +1,3 @@
|
||||||
"""stick the various versioning attributes in here, so we only have to change
|
"""stick the various versioning attributes in here, so we only have to change
|
||||||
them once."""
|
them once."""
|
||||||
version = '0.83.4.1+limnoria (2011-08-10T12:00:42+0200)'
|
version = '0.83.4.1+limnoria (2011-08-13T01:59:18+0200)'
|
||||||
|
|
Loading…
Reference in New Issue