Example #1
0
 def testNickFromHostmask(self):
     self.assertEqual(
         ircutils.nickFromHostmask('[email protected]'), 'nick')
     # Hostmasks with user prefixes are sent via userhost-in-names. We need to
     # properly handle the case where ! is a prefix and not grab '' as the nick
     # instead.
     self.assertEqual(
         ircutils.nickFromHostmask('@[email protected]'), '@nick')
     self.assertEqual(
         ircutils.nickFromHostmask('!@[email protected]'), '!@nick')
Example #2
0
 def testNickFromHostmask(self):
     self.assertEqual(ircutils.nickFromHostmask('[email protected]'),
                      'nick')
     # Hostmasks with user prefixes are sent via userhost-in-names. We need to
     # properly handle the case where ! is a prefix and not grab '' as the nick
     # instead.
     self.assertEqual(ircutils.nickFromHostmask('@[email protected]'),
                      '@nick')
     self.assertEqual(ircutils.nickFromHostmask('!@[email protected]'),
                      '!@nick')
Example #3
0
    def quiet(self, irc, msg, args, channel, nick, expiry):
        """[<channel>] <nick> [<expiry>]

        Quietens <nick> from <channel> for <expiry>.  If <expiry> isn't given,
        the duration is permanent.
        <channel> is only necessary if the message isn't sent in the channel
        itself.
        """
        if irc.isNick(nick):
            bannedNick = nick
            try:
                bannedHostmask = irc.state.nickToHostmask(nick)
            except KeyError:
                irc.error(format(_('I haven\'t seen %s.'), bannedNick), Raise=True)
        else:
            bannedNick = ircutils.nickFromHostmask(nick)
            bannedHostmask = nick
        if not irc.isNick(bannedNick):
            self.log.warning('%q tried to quiet a non nick: %q',
                             msg.prefix, bannedNick)
            raise callbacks.ArgumentError
        banmaskstyle = conf.supybot.protocols.irc.banmask
        banmask = banmaskstyle.makeBanmask(bannedHostmask)
        if ircutils.strEqual(nick, irc.nick):
            irc.error('I cowardly refuse to quiet myself.', Raise=True)
        thismsg=self.registryValue('message')
        self._sendMsg(irc, ircmsgs.mode(channel, ("+q", banmask)))
        if self.registryValue('SendMsgPvt'):
            self._sendMsg(irc, ircmsgs.privmsg(nick,nick+", "+thismsg ))
        else:
            self._sendMsg(irc, ircmsgs.privmsg(channel,nick+", "+thismsg ))
        def f():
            irc.queueMsg(ircmsgs.mode(channel, ("-q", banmask)))
        if expiry:
        	schedule.addEvent(f, expiry)
Example #4
0
 def requestComment(self, irc, channel, ban):
     if not ban or not self.registryValue('request', channel):
         return
     # check the type of the action taken
     mask = ban.mask
     type = guessBanType(mask)
     if type == 'quiet':
         mask = mask[1:]
     # check if type is enabled
     if type not in self.registryValue('request.type', channel):
         return
     prefix = conf.supybot.reply.whenAddressedBy.chars()[0] # prefix char for commands
     # check to who send the request
     try:
         nick = ircutils.nickFromHostmask(ban.who)
     except:
         nick = ban.who
     if nickMatch(nick, self.registryValue('request.ignore', channel)):
         return
     if nickMatch(nick, self.registryValue('request.forward', channel)):
         s = "Please somebody comment on the %s of %s in %s done by %s, use:"\
             " %scomment %s <comment>" %(type, mask, channel, nick, prefix, ban.id)
         self._sendForward(irc, s, channel)
     else:
         # send to op
         s = "Please comment on the %s of %s in %s, use: %scomment %s <comment>" \
                 %(type, mask, channel, prefix, ban.id)
         irc.reply(s, to=nick, private=True)
Example #5
0
	def rsync(self, irc, msg, args):
		self._updateMonitorList(irc)
		
		count = 0
		result = self._radioQuery('areirc')
		for hostmask in result['hostmasks']:
			hostmask = hostmask.encode('ascii')
			if ircutils.nickFromHostmask(hostmask) not in self.monitorList:
				self._radioQuery('authpart', { 'hostmask' : hostmask })
				count += 1
			else:
				hostmaskIRC = irc.state.nickToHostmask(ircutils.nickFromHostmask(hostmask))
				if (hostmask.split('!')[1] != hostmaskIRC.split('!')[1]):
					self._radioQuery('authpart', { 'hostmask' : hostmask })
					count += 1
		reply = u"%i Benutzer entfernt" % count
		irc.reply(reply.encode('utf-8'))
Example #6
0
	def doAccount (self,irc,msg):
		if ircutils.isUserHostmask(msg.prefix):
			nick = ircutils.nickFromHostmask(msg.prefix)
			for channel in irc.state.channels:
				chan = self.getChan(irc,channel)
				if nick in chan.nicks:
					a = chan.nicks[nick]
					account = msg.args[0]
					if account == '*':
						account = ''
					a[1] = account
					chan.nicks[nick] = a
Example #7
0
 def doAccount (self,irc,msg):
     if ircutils.isUserHostmask(msg.prefix):
         nick = ircutils.nickFromHostmask(msg.prefix)
         for channel in irc.state.channels:
             chan = self.getChan(irc,channel)
             if nick in chan.nicks:
                 a = chan.nicks[nick]
                 account = msg.args[0]
                 if account == '*':
                     account = ''
                 a[1] = account
                 chan.nicks[nick] = a
Example #8
0
 def _feedMsg(self,
              query,
              timeout=None,
              to=None,
              frm=None,
              private=False,
              usePrefixChar=True):
     if to is None:
         if private:
             to = self.irc.nick
         else:
             to = self.channel
     if frm is None:
         frm = self.prefix
     if timeout is None:
         timeout = self.timeout
     if self.myVerbose:
         print  # Newline, just like PluginTestCase.
     prefixChars = conf.supybot.reply.whenAddressedBy.chars()
     if query[0] not in prefixChars and usePrefixChar:
         query = prefixChars[0] + query
     msg = ircmsgs.privmsg(to, query, prefix=frm)
     if self.myVerbose:
         print 'Feeding: %r' % msg
     self.irc.feedMsg(msg)
     fed = time.time()
     response = self.irc.takeMsg()
     while response is None and time.time() - fed < timeout:
         time.sleep(0.1)
         drivers.run()
         response = self.irc.takeMsg()
     if response is not None:
         if response.command == 'PRIVMSG':
             args = list(response.args)
             # Strip off nick: at beginning of response.
             if args[1].startswith(self.nick) or \
                args[1].startswith(ircutils.nickFromHostmask(self.prefix)):
                 try:
                     args[1] = args[1].split(' ', 1)[1]
                 except IndexError:
                     # Odd.  We'll skip this.
                     pass
             ret = ircmsgs.privmsg(*args)
         else:
             ret = response
     else:
         ret = None
     if self.myVerbose:
         print 'Returning: %r' % ret
     return ret
Example #9
0
 def testAddFactoid(self):
     self.assertNotError('moo is foo')
     # Check stripping punctuation
     self.assertError('moo!?    is foo') # 'moo' already exists
     self.assertNotError('foo!?    is foo')
     self.assertResponse('foo', 'foo is foo')
     self.assertNotError('bar is <reply>moo is moo')
     self.assertResponse('bar', 'moo is moo')
     # Check substitution
     self.assertNotError('who is <reply>$who')
     self.assertResponse('who', ircutils.nickFromHostmask(self.prefix))
     # Check that actions ("\x01ACTION...") don't match
     m = ircmsgs.action(self.channel, 'is doing something')
     self.irc.feedMsg(m)
     self.assertNoResponse(' ', 1)
Example #10
0
 def testAddFactoid(self):
     self.assertNotError('moo is foo')
     # Check stripping punctuation
     self.assertError('moo!?    is foo')  # 'moo' already exists
     self.assertNotError('foo!?    is foo')
     self.assertResponse('foo', 'foo is foo')
     self.assertNotError('bar is <reply>moo is moo')
     self.assertResponse('bar', 'moo is moo')
     # Check substitution
     self.assertNotError('who is <reply>$who')
     self.assertResponse('who', ircutils.nickFromHostmask(self.prefix))
     # Check that actions ("\x01ACTION...") don't match
     m = ircmsgs.action(self.channel, 'is doing something')
     self.irc.feedMsg(m)
     self.assertNoResponse(' ', 1)
Example #11
0
 def _feedMsg(self, query, timeout=None, to=None, frm=None, private=False,
              usePrefixChar=True):
     if to is None:
         if private:
             to = self.irc.nick
         else:
             to = self.channel
     if frm is None:
         frm = self.prefix
     if timeout is None:
         timeout = self.timeout
     if self.myVerbose:
         print # Newline, just like PluginTestCase.
     prefixChars = conf.supybot.reply.whenAddressedBy.chars()
     if query[0] not in prefixChars and usePrefixChar:
         query = prefixChars[0] + query
     if sys.version_info[0] < 3 and isinstance(query, unicode):
         query = query.encode('utf8') # unicode->str
     msg = ircmsgs.privmsg(to, query, prefix=frm)
     if self.myVerbose:
         print 'Feeding: %r' % msg
     self.irc.feedMsg(msg)
     fed = time.time()
     response = self.irc.takeMsg()
     while response is None and time.time() - fed < timeout:
         time.sleep(0.1)
         drivers.run()
         response = self.irc.takeMsg()
     if response is not None:
         if response.command == 'PRIVMSG':
             args = list(response.args)
             # Strip off nick: at beginning of response.
             if args[1].startswith(self.nick) or \
                args[1].startswith(ircutils.nickFromHostmask(self.prefix)):
                 try:
                     args[1] = args[1].split(' ', 1)[1]
                 except IndexError:
                     # Odd.  We'll skip this.
                     pass
             ret = ircmsgs.privmsg(*args)
         else:
             ret = response
     else:
         ret = None
     if self.myVerbose:
         print 'Returning: %r' % ret
     return ret
Example #12
0
    def doTagmsg(self, irc, msg):
        if REQUEST_TAG not in msg.server_tags:
            return
        if "msgid" not in msg.server_tags:
            return
        if not self._enabled(irc, msg):
            return

        msgid = msg.server_tags["msgid"]

        text = msg.server_tags[REQUEST_TAG]

        # using callbacks._addressed instead of callbacks.addressed, as
        # callbacks.addressed would tag the m
        payload = callbacks._addressed(irc, msg, payload=text)

        if not payload:
            # not addressed
            return

        # marks used by '_addressed' are usually prefixes (char, string,
        # nick), but may also be suffixes (with
        # supybot.reply.whenAddressedBy.nick.atEnd); but there is no way to
        # have it in the middle of the message AFAIK.
        assert payload in text

        if not text.endswith(payload):
            # If there is a suffix, it means the end of the text is used to
            # address the bot, so it can't be a method to be completed.
            return

        autocomplete_response = _getAutocompleteResponse(irc, msg, payload)
        if not autocomplete_response:
            return

        target = msg.channel or ircutils.nickFromHostmask(msg.prefix)
        irc.queueMsg(
            ircmsgs.IrcMsg(
                server_tags={
                    "+draft/reply": msgid,
                    RESPONSE_TAG: autocomplete_response,
                },
                command="TAGMSG",
                args=[target],
            )
        )
Example #13
0
    def undo(self, irc, msg, args, nick):
        """<nick>

        Removes the latest note you sent to <nick>.
        """
        if nick not in self._notes:
            irc.error(_('There are no note waiting for %s.') % nick)
            return
        self._notes[nick].reverse()
        for note in self._notes[nick]:
            if ircutils.nickFromHostmask(note[1]) == msg.nick:
                self._notes[nick].remove(note)
                if len(self._notes[nick]) == 0:
                    del self._notes[nick]
                self._flushNotes()
                irc.replySuccess()
                return
        irc.error(_('There are no note from you waiting for %s.') % nick)
Example #14
0
    def ungrab(self, irc, msg, args, channel, grab):
        """[<channel>] <number>

        Removes the grab <number> (the last by default) on <channel>.
        <channel> is only necessary if the message isn't sent in the channel
        itself.  You may only ungrab quotes you made or grabbed.
        """
        try:
            original = self.db.get(channel, grab)
            if ircutils.nickEqual(ircutils.nickFromHostmask(original.grabber), msg.nick) or ircutils.nickEqual(original.by, msg.nick):
                self.db.remove(channel, grab)
                irc.replySuccess()
            else:
                irc.error('Can only ungrab quotes made or grabbed by you.')
        except dbi.NoRecordError:
            if grab is None:
                irc.error('Nothing to ungrab.')
            else:
                irc.error('Invalid grab number.')
Example #15
0
 def _doKickban(self, irc, channel, operator, target, kickmsg = None, use_time = None, extra_comment = None):
     if not self.registryValue('enabled', channel):
         return
     n = now()
     if use_time:
         n = fromTime(use_time)
     try:
         nick = ircutils.nickFromHostmask(operator)
     except:
         nick = operator
     id = self.db_run("INSERT INTO bans (channel, mask, operator, time, log) values(%s, %s, %s, %s, %s)", 
                       (channel, target, nick, n, '\n'.join(self.logs[channel])), expect_id=True)
     if kickmsg and id and not (kickmsg == nick):
         self.db_run("INSERT INTO comments (ban_id, who, comment, time) values(%s,%s,%s,%s)", (id, nick, kickmsg, n))
     if extra_comment:
         self.db_run("INSERT INTO comments (ban_id, who, comment, time) values(%s,%s,%s,%s)", (id, nick, extra_comment, n))
     if channel not in self.bans:
         self.bans[channel] = []
     ban = Ban(mask=target, who=operator, when=time.mktime(time.gmtime()), id=id)
     self.bans[channel].append(ban)
     return ban
Example #16
0
    def unquiet(self, irc, msg, args, channel, nick):
        """[<channel>] <nick> [<expiry>]

        Quietens <nick> from <channel> for <expiry>.  If <expiry> isn't given,
        the duration is permanent.
        <channel> is only necessary if the message isn't sent in the channel
        itself.
        """
        if irc.isNick(nick):
            bannedNick = nick
            try:
                bannedHostmask = irc.state.nickToHostmask(nick)
            except KeyError:
                irc.error(format(_('I haven\'t seen %s.'), bannedNick), Raise=True)
        else:
            bannedNick = ircutils.nickFromHostmask(nick)
            bannedHostmask = nick
        if not irc.isNick(bannedNick):
            self.log.warning('%q tried to quiet a non nick: %q',
                             msg.prefix, bannedNick)
            raise callbacks.ArgumentError
        banmaskstyle = conf.supybot.protocols.irc.banmask
        banmask = banmaskstyle.makeBanmask(bannedHostmask)
        irc.queueMsg(ircmsgs.mode(channel, ("-q", banmask)))
Example #17
0
 def testNickFromHostmask(self):
     self.assertEqual(
         ircutils.nickFromHostmask('[email protected]'), 'nick')
Example #18
0
    def reviewBans(self, irc=None):
        reviewTime = int(self.registryValue('request.review') * 86400)
        if not reviewTime:
            # time is zero, do nothing
            return
        now = time.mktime(time.gmtime())
        lastreview = self.pendingReviews.time
        self.pendingReviews.time = now # update last time reviewed
        if not lastreview:
            # initialize last time reviewed timestamp
            lastreview = now - reviewTime

        for channel, bans in self.bans.iteritems():
            if not self.registryValue('enabled', channel) \
                    or not self.registryValue('request', channel):
                continue

            for ban in bans:
                if guessBanType(ban.mask) in ('quiet', 'removal'):
                    # skip mutes and kicks
                    continue
                banAge = now - ban.when
                reviewWindow = lastreview - ban.when
                #self.log.debug('review ban: %s ban %s by %s (%s/%s/%s %s)', channel, ban.mask,
                #        ban.who, reviewWindow, reviewTime, banAge, reviewTime - reviewWindow)
                if reviewWindow <= reviewTime < banAge:
                    # ban is old enough, and inside the "review window"
                    try:
                        # ban.who should be a user hostmask
                        nick = ircutils.nickFromHostmask(ban.who)
                        host = ircutils.hostFromHostmask(ban.who)
                    except:
                        if ircutils.isNick(ban.who, strictRfc=True):
                            # ok, op's nick, use it
                            nick = ban.who
                            host = None
                        else:
                            # probably a ban restored by IRC server in a netsplit
                            # XXX see if something can be done about this
                            continue
                    if nickMatch(nick, self.registryValue('request.ignore', channel)):
                        # in the ignore list
                        continue
                    if not ban.id:
                        ban.id = self.get_banId(ban.mask, channel)
                    if nickMatch(nick, self.registryValue('request.forward', channel)):
                        s = "Hi, please somebody review the ban '%s' set by %s on %s in"\
                        " %s, link: %s/bans.cgi?log=%s" %(ban.mask, nick, ban.ascwhen, channel,
                                self.registryValue('bansite'), ban.id)
                        self._sendForward(irc, s, channel)
                    else:
                        s = "Hi, please review the ban '%s' that you set on %s in %s, link:"\
                        " %s/bans.cgi?log=%s" %(ban.mask, ban.ascwhen, channel,
                                self.registryValue('bansite'), ban.id)
                        msg = ircmsgs.privmsg(nick, s)
                        if host in self.pendingReviews \
                            and (nick, msg) not in self.pendingReviews[host]:
                            self.pendingReviews[host].append((nick, msg))
                        else:
                            self.pendingReviews[host] = [(nick, msg)]
                elif banAge < reviewTime:
                    # since we made sure bans are sorted by time, the bans left are more recent
                    break
Example #19
0
 def testNickFromHostmask(self):
     self.assertEqual(ircutils.nickFromHostmask('[email protected]'),
                      'nick')
Example #20
0
 def _ban(self, irc, msg, args,
         channel, optlist, target, expiry, reason, kick):
     # Check that they're not trying to make us kickban ourself.
     if irc.isNick(target):
         bannedNick = target
         try:
             bannedHostmask = irc.state.nickToHostmask(target)
             banmaskstyle = conf.supybot.protocols.irc.banmask
             banmask = banmaskstyle.makeBanmask(bannedHostmask, [o[0] for o in optlist])
         except KeyError:
             if not conf.supybot.protocols.irc.strictRfc() and \
                     target.startswith('$'):
                 # Select the last part, or the whole target:
                 bannedNick = target.split(':')[-1]
                 banmask = bannedHostmask = target
             else:
                 irc.error(format(_('I haven\'t seen %s.'), bannedNick), Raise=True)
     else:
         bannedNick = ircutils.nickFromHostmask(target)
         banmask = bannedHostmask = target
     if not irc.isNick(bannedNick):
         self.log.warning('%q tried to kban a non nick: %q',
                          msg.prefix, bannedNick)
         raise callbacks.ArgumentError
     elif bannedNick == irc.nick:
         self.log.warning('%q tried to make me kban myself.', msg.prefix)
         irc.error(_('I cowardly refuse to kickban myself.'))
         return
     if not reason:
         reason = msg.nick
     capability = ircdb.makeChannelCapability(channel, 'op')
     # Check (again) that they're not trying to make us kickban ourself.
     if ircutils.hostmaskPatternEqual(banmask, irc.prefix):
         if ircutils.hostmaskPatternEqual(bannedHostmask, irc.prefix):
             self.log.warning('%q tried to make me kban myself.',msg.prefix)
             irc.error(_('I cowardly refuse to ban myself.'))
             return
         else:
             self.log.warning('Using exact hostmask since banmask would '
                              'ban myself.')
             banmask = bannedHostmask
     # Now, let's actually get to it.  Check to make sure they have
     # #channel,op and the bannee doesn't have #channel,op; or that the
     # bannee and the banner are both the same person.
     def doBan():
         if irc.state.channels[channel].isOp(bannedNick):
             irc.queueMsg(ircmsgs.deop(channel, bannedNick))
         irc.queueMsg(ircmsgs.ban(channel, banmask))
         if kick:
             irc.queueMsg(ircmsgs.kick(channel, bannedNick, reason))
         if expiry > 0:
             def f():
                 if channel in irc.state.channels and \
                    banmask in irc.state.channels[channel].bans:
                     irc.queueMsg(ircmsgs.unban(channel, banmask))
             schedule.addEvent(f, expiry)
     if bannedNick == msg.nick:
         doBan()
     elif ircdb.checkCapability(msg.prefix, capability):
         if ircdb.checkCapability(bannedHostmask, capability) and \
                 not ircdb.checkCapability(msg.prefix, 'owner'):
             self.log.warning('%s tried to ban %q, but both have %s',
                              msg.prefix, bannedHostmask, capability)
             irc.error(format(_('%s has %s too, you can\'t ban '
                              'them.'), bannedNick, capability))
         else:
             doBan()
     else:
         self.log.warning('%q attempted kban without %s',
                          msg.prefix, capability)
         irc.errorNoCapability(capability)
Example #21
0
 def _formatNote(self, when, whence, note):
     if not self.registryValue('format.senderHostname'):
         whence = ircutils.nickFromHostmask(whence)
     return _('Sent %s: <%s> %s') % (self._timestamp(when), whence, note)
Example #22
0
 def _ban(self, irc, msg, args,
         channel, optlist, target, expiry, reason, kick):
     # Check that they're not trying to make us kickban ourself.
     if irc.isNick(target):
         bannedNick = target
         try:
             bannedHostmask = irc.state.nickToHostmask(target)
             banmaskstyle = conf.supybot.protocols.irc.banmask
             banmask = banmaskstyle.makeBanmask(bannedHostmask, [o[0] for o in optlist])
         except KeyError:
             if not conf.supybot.protocols.irc.strictRfc() and \
                     target.startswith('$'):
                 # Select the last part, or the whole target:
                 bannedNick = target.split(':')[-1]
                 banmask = bannedHostmask = target
             else:
                 irc.error(format(_('I haven\'t seen %s.'), bannedNick), Raise=True)
     else:
         bannedNick = ircutils.nickFromHostmask(target)
         banmask = bannedHostmask = target
     if not irc.isNick(bannedNick):
         self.log.warning('%q tried to kban a non nick: %q',
                          msg.prefix, bannedNick)
         raise callbacks.ArgumentError
     elif bannedNick == irc.nick:
         self.log.warning('%q tried to make me kban myself.', msg.prefix)
         irc.error(_('I cowardly refuse to kickban myself.'))
         return
     if not reason:
         reason = msg.nick
     capability = ircdb.makeChannelCapability(channel, 'op')
     # Check (again) that they're not trying to make us kickban ourself.
     if ircutils.hostmaskPatternEqual(banmask, irc.prefix):
         if ircutils.hostmaskPatternEqual(bannedHostmask, irc.prefix):
             self.log.warning('%q tried to make me kban myself.',msg.prefix)
             irc.error(_('I cowardly refuse to ban myself.'))
             return
         else:
             self.log.warning('Using exact hostmask since banmask would '
                              'ban myself.')
             banmask = bannedHostmask
     # Now, let's actually get to it.  Check to make sure they have
     # #channel,op and the bannee doesn't have #channel,op; or that the
     # bannee and the banner are both the same person.
     def doBan():
         if irc.state.channels[channel].isOp(bannedNick):
             irc.queueMsg(ircmsgs.deop(channel, bannedNick))
         irc.queueMsg(ircmsgs.ban(channel, banmask))
         if kick:
             irc.queueMsg(ircmsgs.kick(channel, bannedNick, reason))
         if expiry > 0:
             def f():
                 if channel in irc.state.channels and \
                    banmask in irc.state.channels[channel].bans:
                     irc.queueMsg(ircmsgs.unban(channel, banmask))
             schedule.addEvent(f, expiry)
     if bannedNick == msg.nick:
         doBan()
     elif ircdb.checkCapability(msg.prefix, capability):
         if ircdb.checkCapability(bannedHostmask, capability) and \
                 not ircdb.checkCapability(msg.prefix, 'owner'):
             self.log.warning('%s tried to ban %q, but both have %s',
                              msg.prefix, bannedHostmask, capability)
             irc.error(format(_('%s has %s too, you can\'t ban '
                              'them.'), bannedNick, capability))
         else:
             doBan()
     else:
         self.log.warning('%q attempted kban without %s',
                          msg.prefix, capability)
         irc.errorNoCapability(capability)
Example #23
0
 def testNickFromHostmask(self):
     self.assertEqual(ircutils.nickFromHostmask("[email protected]"), "nick")