Made Proxy Irc objects map to the same dictionary slot, so we don't need to worry about calling getRealIrc all the time.

This commit is contained in:
Jeremy Fincher 2005-03-28 13:00:37 +00:00
parent 5ce2baa2d2
commit 0773aa31e5
3 changed files with 89 additions and 41 deletions

View File

@ -519,7 +519,59 @@ class RichReplyMethods(object):
_repr = repr
class IrcObjectProxy(RichReplyMethods):
class IrcReplyProxy(RichReplyMethods):
"""This class is a thin wrapper around an irclib.Irc object that gives it
the reply() and error() methods (as well as everything in RichReplyMethods,
based on those two)."""
def __init__(self, irc, msg):
self.irc = irc
self.msg = msg
def getRealIrc(self):
if isinstance(self.irc, irclib.Irc):
return self.irc
else:
return self.irc.getRealIrc()
# This should make us be considered equal to our irclib.Irc object for
# hashing; an important thing (no more "too many open files" exceptions :))
def __hash__(self):
return hash(self.getRealIrc())
def __eq__(self, other):
return self.getRealIrc() == other
__req__ = __eq__
def __ne__(self, other):
return not (self == other)
__rne__ = __ne__
def error(self, s, msg=None, **kwargs):
if 'Raise' in kwargs and kwargs['Raise']:
if s:
raise Error, s
else:
raise ArgumentError
if msg is None:
msg = self.msg
m = error(msg, s, **kwargs)
self.irc.queueMsg(m)
return m
def reply(self, s, msg=None, **kwargs):
if msg is None:
msg = self.msg
assert not isinstance(s, ircmsgs.IrcMsg), \
'Old code alert: there is no longer a "msg" argument to reply.'
kwargs.pop('noLengthCheck', None)
m = reply(msg, s, **kwargs)
self.irc.queueMsg(m)
return m
def __getattr__(self, attr):
return getattr(self.irc, attr)
SimpleProxy = IrcReplyProxy # Backwards-compatibility
class IrcObjectProxy(IrcReplyProxy):
"A proxy object to allow proper nested of commands (even threaded ones)."
_mores = ircutils.IrcDict()
def __init__(self, irc, msg, args, nested=0):
@ -1204,45 +1256,6 @@ class Plugin(PluginMixin, Commands):
Privmsg = Plugin # Backwards compatibility.
class SimpleProxy(RichReplyMethods):
"""This class is a thin wrapper around an irclib.Irc object that gives it
the reply() and error() methods (as well as everything in RichReplyMethods,
based on those two)."""
def __init__(self, irc, msg):
self.irc = irc
self.msg = msg
def getRealIrc(self):
if isinstance(self.irc, irclib.Irc):
return self.irc
else:
return self.irc.getRealIrc()
def error(self, s, msg=None, **kwargs):
if 'Raise' in kwargs and kwargs['Raise']:
if s:
raise Error, s
else:
raise ArgumentError
if msg is None:
msg = self.msg
m = error(msg, s, **kwargs)
self.irc.queueMsg(m)
return m
def reply(self, s, msg=None, **kwargs):
if msg is None:
msg = self.msg
assert not isinstance(s, ircmsgs.IrcMsg), \
'Old code alert: there is no longer a "msg" argument to reply.'
kwargs.pop('noLengthCheck', None)
m = reply(msg, s, **kwargs)
self.irc.queueMsg(m)
return m
def __getattr__(self, attr):
return getattr(self.irc, attr)
class PluginRegexp(Plugin):
"""Same as Plugin, except allows the user to also include regexp-based
callbacks. All regexp-based callbacks must be specified in a set (or

View File

@ -975,7 +975,12 @@ class Irc(IrcCommandDispatcher):
return id(self)
def __eq__(self, other):
# We check isinstance here, so that if some proxy object (like those
# defined in callbacks.py) has overridden __eq__, it takes precedence.
if isinstance(other, self.__class__):
return id(self) == id(other)
else:
return other == self
def __ne__(self, other):
return not (self == other)

View File

@ -613,6 +613,36 @@ class WithPrivateNoticeTestCase(ChannelPluginTestCase):
finally:
conf.supybot.reply.withNoticeWhenPrivate.setValue(original)
class ProxyTestCase(SupyTestCase):
def testHashing(self):
msg = ircmsgs.ping('0')
irc = irclib.Irc('test')
proxy = callbacks.SimpleProxy(irc, msg)
# First one way...
self.failIf(proxy != irc)
self.failUnless(proxy == irc)
self.assertEqual(hash(proxy), hash(irc))
# Then the other!
self.failIf(irc != proxy)
self.failUnless(irc == proxy)
self.assertEqual(hash(irc), hash(proxy))
# And now dictionaries...
d = {}
d[irc] = 'foo'
self.failUnless(len(d) == 1)
self.failUnless(d[irc] == 'foo')
self.failUnless(d[proxy] == 'foo')
d[proxy] = 'bar'
self.failUnless(len(d) == 1)
self.failUnless(d[irc] == 'bar')
self.failUnless(d[proxy] == 'bar')
d[irc] = 'foo'
self.failUnless(len(d) == 1)
self.failUnless(d[irc] == 'foo')
self.failUnless(d[proxy] == 'foo')
# vim:set shiftwidth=4 tabstop=4 expandtab textwidth=79: