Пример #1
0
def _get_channels_per_network(cfg):
    hooks = cfg.get('hooks', {})
    network_info = copy.deepcopy(cfg['networks'])
    for net_key in network_info:
        network_info[net_key]['channels'] = []

    for hook in hooks:
        network = hook['network']
        if network not in network_info:
            raise Exception("Network '{network}' not configured"
                            .format(network=network))

        reports = hook['reports']
        for ch in reports:
            current_channels = network_info[network]['channels']
            if is_channel(ch) and ch not in current_channels:
                print("Appending {channel} ({network})"
                      .format(channel=ch, network=network))
                network_info[network]['channels'].append(ch)

    watchers = cfg.get('watchers', {})
    print(watchers)
    for watcher in watchers:
        network = watcher['network']
        channel = watcher['channel']
        current_channels = network_info[network]['channels']
        if channel not in current_channels:
            print("Appending {channel} ({network})"
                  .format(channel=channel, network=network))
            network_info[network]['channels'].append(channel)

    return network_info
Пример #2
0
 def do_part(self, connection, event):
     """Part a channel target given by the bot controller."""
     arguments = event.arguments[0].split()
     try:
         if is_channel(arguments[1]):
             connection.part(arguments[1])
     except IndexError:
         pass
Пример #3
0
 def join_channel(self, params):
     """Join a channel."""
     channel = params.split(" ", 1)
     self.log.info("Joining %s" % channel[0])
     if irclib.is_channel(channel[0]):
         self.channels.append(channel[0])
         if len(channel) > 1:
             self.connection.join(channel[0], channel[1])
         else:
             self.connection.join(channel[0])
Пример #4
0
 def join_channel(self, params):
     """Join a channel."""
     channel = params.split(" ", 1)
     self.reply("Joining %s" % channel[0])
     if irclib.is_channel(channel[0]):
         self.channels.append(channel[0])
         if len(channel) > 1:
             self.connection.join(channel[0], channel[1])
         else:
             self.connection.join(channel[0])
Пример #5
0
 def dispatch(self, reply):
     """Dispatch message as notice."""
     _reply = self._mangle_msg(reply)
     for line in _reply:
         self.irc.notice(self.target, line)
         if irclib.is_channel(self.target):
             self.log.info("-%s- <%s> %s" % (self.target, self.irc.nick,
                           line))
         else:
             self.log.info("<%s> %s" % (self.irc.nick, line))
Пример #6
0
    def on_welcome(self, connection, _event):
        """Join channels upon successful connection."""
        if self.identify_password:
            self.privmsg("NickServ", "IDENTIFY %s" % self.identify_password)

        for channel in self.channels:
            channel = channel.split(" ", 1)
            if irclib.is_channel(channel[0]):
                if len(channel) > 1:
                    connection.join(channel[0], channel[1])
                else:
                    connection.join(channel[0])
Пример #7
0
    def on_welcome(self, connection, _event):
        """Join channels upon successful connection."""
        if self.identify_password:
            self.privmsg("NickServ", "IDENTIFY %s" % self.identify_password)

        for channel in self.channels:
            channel = channel.split(" ", 1)
            if irclib.is_channel(channel[0]):
                if len(channel) > 1:
                    connection.join(channel[0], channel[1])
                else:
                    connection.join(channel[0])
Пример #8
0
def post_to_irc(msg, host, port, nick, ident, realname, target):
    """
    Log into an IRC server and send a message to a channel.
    """
    global IRC_CLIENT, IRC_SERVER
    if IRC_CLIENT is None:
        IRC_CLIENT = client.Reactor()
        IRC_SERVER = IRC_CLIENT.server()

    IRC_SERVER.connect(host, port, nick)
    if client.is_channel(target):
        IRC_SERVER.join(target)
    IRC_SERVER.privmsg(target, msg)
Пример #9
0
 def is_configured(cls):
     if not (hasattr(settings, 'IRC')
             and hasattr(settings, 'IRC_SOCKET_PATH')
             and hasattr(settings, 'IRC_ALLOWED_CHAR')):
         return False
     for conf in settings.IRC:
         if not (conf.get('nick') and conf.get('server')
                 and conf.get('channels')):
             return False
         for chan in conf['channels']:
             if not ('name' in chan and is_channel(chan['name'])):
                 return False
     return True
Пример #10
0
def post_to_irc(msg, host, port, nick, ident, realname, target):
    """
    Log into an IRC server and send a message to a channel.
    """
    global IRC_CLIENT, IRC_SERVER
    if IRC_CLIENT is None:
        IRC_CLIENT = client.Reactor()
        IRC_SERVER = IRC_CLIENT.server()

    IRC_SERVER.connect(host, port, nick)
    if client.is_channel(target):
        IRC_SERVER.join(target)
    for line in msg.splitlines():
        IRC_SERVER.privmsg(target, line)
Пример #11
0
 def is_configured(cls):
     if not (hasattr(settings, 'IRC') and
             hasattr(settings, 'IRC_SOCKET_PATH') and
             hasattr(settings, 'IRC_ALLOWED_CHAR')):
         return False
     for conf in settings.IRC:
         if not (conf.get('nick') and
                 conf.get('server') and
                 conf.get('channels')):
             return False
         for chan in conf['channels']:
             if not ('name' in chan and is_channel(chan['name'])):
                 return False
     return True
Пример #12
0
 def do_join(self, connection, event):
     """Join a channel target given by the bot controller."""
     arguments = event.arguments[0].split()
     usage_msg = [
         "Usage: join <channel name> <invite_threshold> <part_threshold>",
         "Example: join #test 15 12"
     ]
     try:
         if is_channel(arguments[1]):
             connection.join(arguments[1])
     except IndexError:
         for line in usage_msg:
             connection.notice(event.source.nick, line)
     try:
         if arguments[1] not in self.config and is_channel(arguments[1]):
             self.config[arguments[1]] = Registrar(arguments[1],
                                                   int(arguments[2]),
                                                   int(arguments[3]))
             self.config.save()
     except IndexError:
         for line in usage_msg:
             connection.notice(event.source.nick, line)
     connection.names(arguments[1])
Пример #13
0
 def do_join(self, connection, event):
     """Join a channel specified by the bot controller."""
     arguments = event.arguments[0].split()
     try:
         if is_channel(arguments[1]):
             connection.join(arguments[1])
             self._channel_table[arguments[1].lower()] = Pomodoro(
                 connection,
                 arguments[1].lower())
         else:
             connection.notice(event.source.nick,
                               "'" + arguments[1] + "' is not a channel.")
     except IndexError:
         usage_msg = "Usage: join <channel> Example: join #test"
         connection.notice(event.source.nick, usage_msg)
Пример #14
0
 def dispatch(self, reply):
     """dispatch message as a reply."""
     _reply = self._mangle_msg(reply)
     for line in _reply:
         if self.irc.addressed:
             source = self.source.split("!")[0]
             self.irc.privmsg(self.target, "%s: %s" % (source, line))
             self.log.info("-%s- <%s> %s: %s" % (self.target, self.irc.nick,
                           source, line))
         else:
             self.irc.privmsg(self.target, line)
             if irclib.is_channel(self.target):
                 self.log.info("-%s- <%s> %s" % (self.target, self.irc.nick,
                               line))
             else:
                 self.log.info("<%s> %s" % (self.irc.nick, line))
Пример #15
0
    def on_privmsg(self, c, e):
        logging.debug("on_privmsg")

        source = e.source.nick
        target = e.target if is_channel( e.target ) else source
        message = e.arguments[0]

        self.__module_handle('privmsg', source=source, target=target, message=message)
        try:
            self.__process_command( c, e )
        except BotExitException as e:
            raise e
        except BotReloadException as e:
            self.connection.disconnect( "Reloading bot..." )
            self.modules.unload()
            raise e
        except Exception as e:
            logging.exception( 'Error in __process_command: %s', e )
Пример #16
0
    def on_privmsg(self, c, e):
        logging.debug("on_privmsg")

        source = e.source.nick
        target = e.target if is_channel( e.target ) else source
        message = e.arguments[0]

        self.__module_handle('privmsg', source=source, target=target, message=message)
        try:
            self.__process_command( c, e )
        except BotExitException as e:
            raise e
        except BotReloadException as e:
            self.connection.disconnect( "Reloading bot..." )
            self.modules.unload()
            raise e
        except Exception as e:
            logging.exception( 'Error in __process_command: %s', e )
Пример #17
0
    def wrapper(self, bot, connection, event):
        line = ''.join(event.arguments)
        speaker = event.source
        addressee, message = parse_line(line)

        public = ic.is_channel(event.target)
        to_self = is_self(bot, addressee) or not public

        if public and to_self:
            reply = Reply(speaker.nick, event.target, connection)
        elif public and not to_self:
            reply = Reply(addressee, event.target, connection)
        elif not public:
            addressee = bot._nickname
            reply = PrivateReply(event.source.nick, connection)
        else:
            log.warn("Couldn't determine speaker for event: %r", event)

        return method(self, bot, speaker, addressee, message, reply)
Пример #18
0
    def __process_command( self, c, e ):
        """Process a message coming from the server."""
        message = e.arguments[0]
        # commands have to start with !
        if message[0] != '!':
            return
        # strip the ! off, and split the message
        args = message[1:].split()
        # cmd is the first item
        cmd = args.pop(0).strip()
        # test for admin
        admin = e.source.userhost in self.admin
        if not admin:
            if e.target in self.admin_channels and e.target in self.channel_ops and e.source.nick in self.channel_ops[ e.target ]:
                admin = True

        # nick is the sender of the message, target is either a channel or the sender.
        source = e.source.nick
        target = e.target if is_channel(e.target) else source

        # see if there is a module that is willing to handle this, and make it so.
        logging.debug( '__process_command (src: %s; tgt: %s; cmd: %s; args: %s; admin: %s)', source, target, cmd, args, admin )

        # handle die outside of module (in case module is dead :( )
        if admin:
            if cmd == 'die':
                self.notice( source, 'Goodbye cruel world!' )
                raise BotExitException
            elif cmd == 'jump':
                self.jump_server()
            elif cmd == 'restart_class':
                raise BotReloadException
            # config commands
            elif cmd == 'get_config' and len( args ) <= 2:
                if len( args ) == 2:
                    try:
                        value = self.get_config( args[0], args[1] )
                        self.notice( source, 'config[{0}][{1}] = {2}'.format( args[0], args[1], value ) )
                    except:
                        self.notice( source, 'config[{0}][{1}] not set'.format( *args ) )
                elif len( args ) == 1:
                    try:
                        values = self.get_config( args[0] )
                        if len( values ) > 0:
                            self.notice( source, 'config[{}]: '.format( args[0] ) + ', '.join( [ '{}: "{}"'.format( k,v ) for ( k, v ) in values.items() ] ) )
                        else:
                            self.notice( source, 'config[{}] is empty'.format( args[0] ) )
                    except:
                        self.notice( source, 'config[{}] not set'.format( args[0] ) )
                else:
                    try:
                        self.notice( source, 'config groups: ' + ', '.join( self.get_config_groups() ) )
                    except Exception as e:
                        self.notice( source, 'No config groups: {}'.format( e ) )
            elif cmd == 'set_config' and len( args ) >= 2:
                if len( args ) >= 3:
                    config_val = ' '.join( args[2:] )
                else:
                    config_val = None
                try:
                    self.set_config( args[0], args[1], config_val )
                    self.notice( source, 'Set config setting' if config_val else 'Cleared config setting' )
                except Exception as e:
                    self.notice( source, 'Failed setting/clearing config setting: {0}'.format( e ) )
            # other base admin commands
            elif cmd == 'raw':
                self.connection.send_raw( ' '.join( args ) )
                return
            elif cmd == 'admins':
                self.notice( source, 'Current operators:' )
                self.notice( source, ' - global: {0}'.format( ' '.join( self.admin ) ) )
                for chan in [ chan for chan in self.admin_channels if chan in self.channel_ops ]:
                    self.notice( source, ' - {0}: {1}'.format( chan, ' '.join( self.channel_ops[ chan ] ) ) )
                return

        if cmd == 'help':
            if len( args ) > 0:
                if args[0] == 'module':
                    if len( args ) < 2:
                        pass
                    elif self.modules.module_is_loaded( args[1] ):
                        module = self.modules.get_module( args[1] )
                        self.notice( target, module.__doc__ )
                else:
                    for ( module_name, module ) in self.modules.get_loaded_modules():
                        if module.has_cmd( args[0] ):
                            self.notice( target, module.get_cmd( args[0] ).__doc__ )
            else:
                self.notice( target, '!help: this help text (send !help <command> for command help, send !help module <module> for module help)' )
                for ( module_name, module ) in [ lst for lst in self.modules.get_loaded_modules() if lst[1].has_commands and not lst[1].admin_only ]:
                    cmds = module.get_cmd_list()
                    self.notice( target, ' * {0}: {1}'.format( module_name, ', '.join( cmds ) if len( cmds ) > 0 else 'No commands' ) )

        elif admin and cmd == 'admin_help':
            if len( args ) > 0:
                for ( module_name, module ) in self.modules.get_loaded_modules():
                    if module.has_admin_cmd( args[0] ):
                        self.notice( source, module.get_admin_cmd( args[0] ).__doc__ )
            else:
                self.notice( source, '!admin_help: this help text (send !admin_help <command> for command help' )
                self.notice( source, '!die:                                   kill the bot' )
                self.notice( source, '!raw:                                   send raw irc command' )
                self.notice( source, '!admins:                                see who are admin' )
                self.notice( source, '!restart_class:                         restart the main Bot class' )
                for ( module_name, module ) in self.modules.get_loaded_modules():
                    cmds = module.get_admin_cmd_list()
                    if len( cmds ) > 0:
                        self.notice( source, ' * {0}: {1}'.format( module_name, ', '.join( cmds ) ) )
        else:
            for ( module_name, module ) in self.modules.get_loaded_modules():
                try:
                    if module.has_cmd( cmd ):
                        lines = module.get_cmd( cmd )(args=args, source=source, target=target, admin=admin)
                        if lines:
                            for line in lines:
                                self.notice( target, line )
                    elif admin and module.has_admin_cmd( cmd ):
                        lines = module.get_admin_cmd(cmd)(args=args, source=source, target=target, admin=admin)
                        if lines:
                            for line in lines:
                                self.notice( source, line )
                except Exception as e:
                    logging.exception( "Module '{0}' handle error: {1}".format( module_name, e ) )
Пример #19
0
    def on_pubmsg(self, c, e):
        nick = e.source.nick
		target = e.target if is_channel(e.target) else nick
		line = e.arguments[0]
Пример #20
0
	def on_pubmsg(self, c, e):
		nick = e.source.nick
		target = e.target if is_channel(e.target) else nick
		def reply(msg):
			self.send(target, msg)
		def dm(msg):
			self.send(nick, msg)
		line = UnicodeDammit(e.arguments[0]).unicode_markup
		log('   \033[37m{}→{}\033[0m'.format(nick, line))
		a = line.split(":", 1)
		if len(a) > 1 and a[0].lower() == self.nick:
			self.do_command(e, a[1].strip().lower(), nick, target, reply, dm)
			return

		# zeltofilter
		if 'zeltoph' in nick:
			return

		foo = settings.VIPS.get(nick, 0)
		if random() < foo:
			self.kick(nick)
	
		match = re.match('.*┻━┻.*', line)
		if match:
			reply('┬─┬ノ(ಠ_ಠノ)')
			return

		match = re.match('^({} *:)? *chaos-?([☆★☼☀*]|sternchen) *: ?(.*)$'.format(self.nick), line)
		if match:
			newcs = match.group(3)
			self.chaossternchen.append(newcs)
			self.sendchan('Chaos-☆ Nr. {} notiert: {}'.format(len(self.chaossternchen), newcs))
			return

		if line.startswith('.wiki '):
			wikipage = line[len('.wiki '):].strip()
			if re.match('^[-_+\w]+$', wikipage):
				wikiurl = 'http://afra-berlin.de/dokuwiki/doku.php?id={}'.format(wikipage)
				if 'Dieses Thema existiert noch nicht' in requests.get(wikiurl).text:
					reply("I'm sorry, I can't find a wiki page with that name.")
				else:
					reply(wikiurl)
			else:
				reply('Try to troll somebot else.')
			return

		if line == 'wat?':
			reply("I don't have a clue.")
			return
		if re.match('^hail eris[.!]* ', line.lower()):
			reply("All Hail Discordia!")
			return
		m = re.findall('(^|\s)?(gh?ah?nh?dh?ih?)(\s|$)?', line, re.IGNORECASE)
		for _1,match,_2 in m:
			if not re.match('(^|\s)?gandhi(\s|$)?', match, re.IGNORECASE):
				self.kick(nick, "It's spelled Gandhi")
				return
		if re.search('https?://[-a-z0-9.]*facebook.com', line.lower()):
			reply('A facebook link? srsly? Get some self-respect!')
			return
		match = re.search('https?://pr0gramm.com/#(newest/\*/[0-9/]*)', line.lower())
		if match:
			reply('Fixed that pr0gramm link for you: http://pr0gramm.com/static/'+match.group(1))
			return
		if line == 'moin':
			self.moincount += 1
			if self.moincount == 5:
				reply('moin')
			return
		else:
			self.moincount = 0
		if line.lstrip('.!#').startswith('eta '):
			eta = line[4:].strip()
			with self.db as db:
				db.execute("DELETE FROM etas WHERE nick=?", (nick,))
				if eta:
					db.execute("INSERT INTO etas VALUES (DATETIME('now'), ?, ?)", (nick, eta))
			dm('ETA registered. Thanks!')
			return
		m = re.findall(URL_REGEX, line.lower())
		for url,*_ in m:
			res = requests.get(url)
			if res.status_code == requests.codes.ok:
				soup = BeautifulSoup(res.text)
				reply(soup.title.string)
		m = re.findall('(^|\s)(afra)(\s|$)', line, re.IGNORECASE)
		for _1,match,_2 in m:
			if match != 'AfRA' and match != 'afra' and random() < 0.1:
				reply("I'm sure you meant AfRA, not "+match)
				return
Пример #21
0
 def need_join(self):
     """Return True if this channel needs to be joined"""
     return is_channel(self.name) and not self._is_joined
Пример #22
0
def on_connect(connection, event):
    if client.is_channel(target):
        connection.join(target)
        return
    main_loop(connection)
Пример #23
0
    def __process_command(self, c, e):
        """Process a message coming from the server."""
        message = e.arguments[0]
        # commands have to start with !
        if message[0] != '!':
            return
        # strip the ! off, and split the message into command and arguments
        split_message = message[1:].split(None, 1)
        cmd = split_message.pop(0).strip()
        raw_args = split_message[0] if len(split_message) else ''
        arglist = raw_args.split()

        # test for admin
        admin = e.source.userhost in self.admin
        if not admin:
            if e.target in self.admin_channels and e.target in self.channel_ops and e.source.nick in self.channel_ops[
                    e.target]:
                admin = True

        # nick is the sender of the message, target is either a channel or the sender.
        source = e.source.nick
        target = e.target if is_channel(e.target) else source

        # see if there is a module that is willing to handle this, and make it so.
        logging.debug(
            '__process_command (src: %s; tgt: %s; cmd: %s; args: %s; admin: %s)',
            source, target, cmd, raw_args, admin)

        # handle die outside of module (in case module is dead :( )
        if admin:
            if cmd == 'die':
                self.notice(source, 'Goodbye cruel world!')
                raise BotExitException
            elif cmd == 'jump':
                self.jump_server()
            elif cmd == 'restart_class':
                self.notice(source, 'Restarting...')
                raise BotReloadException
            # config commands
            elif cmd == 'get_config' and len(arglist) <= 2:
                if len(arglist) == 2:
                    try:
                        value = self.get_config(arglist[0], arglist[1])
                        self.notice(
                            source, 'config[{0}][{1}] = {2}'.format(
                                arglist[0], arglist[1], value))
                    except:
                        self.notice(
                            source,
                            'config[{0}][{1}] not set'.format(*arglist))
                elif len(arglist) == 1:
                    try:
                        values = self.get_config(arglist[0])
                        if len(values) > 0:
                            self.notice(
                                source,
                                'config[{}]: '.format(arglist[0]) + ', '.join([
                                    '{}: "{}"'.format(k, v)
                                    for (k, v) in values.items()
                                ]))
                        else:
                            self.notice(
                                source,
                                'config[{}] is empty'.format(arglist[0]))
                    except:
                        self.notice(source,
                                    'config[{}] not set'.format(arglist[0]))
                else:
                    try:
                        self.notice(
                            source, 'config groups: ' +
                            ', '.join(self.get_config_groups()))
                    except Exception as e:
                        self.notice(source, 'No config groups: {}'.format(e))
            elif cmd == 'set_config' and len(arglist) >= 2:
                if len(arglist) >= 3:
                    config_val = ' '.join(arglist[2:])
                else:
                    config_val = None
                try:
                    self.set_config(arglist[0], arglist[1], config_val)
                    self.notice(
                        source, 'Set config setting'
                        if config_val else 'Cleared config setting')
                except Exception as e:
                    self.notice(
                        source,
                        'Failed setting/clearing config setting: {0}'.format(
                            e))
            # other base admin commands
            elif cmd == 'raw':
                self.connection.send_raw(raw_args)
                return
            elif cmd == 'admins':
                self.notice(source, 'Current operators:')
                self.notice(source,
                            ' - global: {0}'.format(' '.join(self.admin)))
                for chan in [
                        chan for chan in self.admin_channels
                        if chan in self.channel_ops
                ]:
                    self.notice(
                        source,
                        ' - {0}: {1}'.format(chan,
                                             ' '.join(self.channel_ops[chan])))
                return

        if False and cmd == 'help':
            if len(arglist) > 0:
                if arglist[0] == 'module':
                    if len(arglist) < 2:
                        pass
                    elif self.modules.module_is_loaded(arglist[1]):
                        module = self.modules.get_module(arglist[1])
                        self.notice(target, module.__doc__)
                else:
                    for (module_name,
                         module) in self.modules.get_loaded_modules():
                        if module.has_cmd(arglist[0]):
                            self.notice(target,
                                        module.get_cmd(arglist[0]).__doc__)
            else:
                self.notice(
                    target,
                    '!help: this help text (send !help <command> for command help, send !help module <module> for module help)'
                )
                for (module_name, module) in [
                        lst for lst in self.modules.get_loaded_modules()
                        if lst[1].has_commands and not lst[1].admin_only
                ]:
                    cmds = module.get_cmd_list()
                    self.notice(
                        target, ' * {0}: {1}'.format(
                            module_name, ', '.join(cmds)
                            if len(cmds) > 0 else 'No commands'))

        elif False and admin and cmd == 'admin_help':
            if len(arglist) > 0:
                for (module_name, module) in self.modules.get_loaded_modules():
                    if module.has_admin_cmd(arglist[0]):
                        self.notice(source,
                                    module.get_admin_cmd(arglist[0]).__doc__)
            else:
                self.notice(
                    source,
                    '!admin_help: this help text (send !admin_help <command> for command help'
                )
                self.notice(
                    source,
                    '!die:                                   kill the bot')
                self.notice(
                    source,
                    '!raw:                                   send raw irc command'
                )
                self.notice(
                    source,
                    '!admins:                                see who are admin'
                )
                self.notice(
                    source,
                    '!restart_class:                         restart the main Bot class'
                )
                for (module_name, module) in self.modules.get_loaded_modules():
                    cmds = module.get_admin_cmd_list()
                    if len(cmds) > 0:
                        self.notice(
                            source,
                            ' * {0}: {1}'.format(module_name, ', '.join(cmds)))
        else:
            for (module_name, module) in self.modules.get_loaded_modules():
                try:
                    if module.has_cmd(cmd):
                        lines = module.get_cmd(cmd)(args=arglist,
                                                    arglist=arglist,
                                                    raw_args=raw_args,
                                                    source=source,
                                                    target=target,
                                                    admin=admin)
                        if lines:
                            for line in lines:
                                self.notice(target, line)
                    elif admin and module.has_admin_cmd(cmd):
                        lines = module.get_admin_cmd(cmd)(args=arglist,
                                                          arglist=arglist,
                                                          raw_args=raw_args,
                                                          source=source,
                                                          target=target,
                                                          admin=admin)
                        if lines:
                            for line in lines:
                                self.notice(source, line)
                except Exception as e:
                    logging.exception("Module '{0}' handle error: {1}".format(
                        module_name, e))
Пример #24
0
 def on_connect(self, connection: Connection, event: Event) -> None:
     if is_channel(self.channel):
         connection.join(self.channel)
         return
     self.main_loop(connection)
Пример #25
0
	def is_channel(self):
		return client.is_channel(self.target)
Пример #26
0
    def __process_command(self, c, e):
        """Process a message coming from the server."""
        message = e.arguments[0]
        # commands have to start with !
        if message[0] != "!":
            return
        # strip the ! off, and split the message into command and arguments
        split_message = message[1:].split(None, 1)
        cmd = split_message.pop(0).strip()
        raw_args = split_message[0] if len(split_message) else ""
        arglist = raw_args.split()

        # test for admin
        admin = e.source.userhost in self.admin
        if not admin:
            if (
                e.target in self.admin_channels
                and e.target in self.channel_ops
                and e.source.nick in self.channel_ops[e.target]
            ):
                admin = True

        # nick is the sender of the message, target is either a channel or the sender.
        source = e.source.nick
        target = e.target if is_channel(e.target) else source

        # see if there is a module that is willing to handle this, and make it so.
        logging.debug(
            "__process_command (src: %s; tgt: %s; cmd: %s; args: %s; admin: %s)", source, target, cmd, raw_args, admin
        )

        # handle die outside of module (in case module is dead :( )
        if admin:
            if cmd == "die":
                self.notice(source, "Goodbye cruel world!")
                raise BotExitException
            elif cmd == "jump":
                self.jump_server()
            elif cmd == "restart_class":
                self.notice(source, "Restarting...")
                raise BotReloadException
            # config commands
            elif cmd == "get_config" and len(arglist) <= 2:
                if len(arglist) == 2:
                    try:
                        value = self.get_config(arglist[0], arglist[1])
                        self.notice(source, "config[{0}][{1}] = {2}".format(arglist[0], arglist[1], value))
                    except:
                        self.notice(source, "config[{0}][{1}] not set".format(*arglist))
                elif len(arglist) == 1:
                    try:
                        values = self.get_config(arglist[0])
                        if len(values) > 0:
                            self.notice(
                                source,
                                "config[{}]: ".format(arglist[0])
                                + ", ".join(['{}: "{}"'.format(k, v) for (k, v) in values.items()]),
                            )
                        else:
                            self.notice(source, "config[{}] is empty".format(arglist[0]))
                    except:
                        self.notice(source, "config[{}] not set".format(arglist[0]))
                else:
                    try:
                        self.notice(source, "config groups: " + ", ".join(self.get_config_groups()))
                    except Exception as e:
                        self.notice(source, "No config groups: {}".format(e))
            elif cmd == "set_config" and len(arglist) >= 2:
                if len(arglist) >= 3:
                    config_val = " ".join(arglist[2:])
                else:
                    config_val = None
                try:
                    self.set_config(arglist[0], arglist[1], config_val)
                    self.notice(source, "Set config setting" if config_val else "Cleared config setting")
                except Exception as e:
                    self.notice(source, "Failed setting/clearing config setting: {0}".format(e))
            # other base admin commands
            elif cmd == "raw":
                self.connection.send_raw(raw_args)
                return
            elif cmd == "admins":
                self.notice(source, "Current operators:")
                self.notice(source, " - global: {0}".format(" ".join(self.admin)))
                for chan in [chan for chan in self.admin_channels if chan in self.channel_ops]:
                    self.notice(source, " - {0}: {1}".format(chan, " ".join(self.channel_ops[chan])))
                return

        if False and cmd == "help":
            if len(arglist) > 0:
                if arglist[0] == "module":
                    if len(arglist) < 2:
                        pass
                    elif self.modules.module_is_loaded(arglist[1]):
                        module = self.modules.get_module(arglist[1])
                        self.notice(target, module.__doc__)
                else:
                    for (module_name, module) in self.modules.get_loaded_modules():
                        if module.has_cmd(arglist[0]):
                            self.notice(target, module.get_cmd(arglist[0]).__doc__)
            else:
                self.notice(
                    target,
                    "!help: this help text (send !help <command> for command help, send !help module <module> for module help)",
                )
                for (module_name, module) in [
                    lst for lst in self.modules.get_loaded_modules() if lst[1].has_commands and not lst[1].admin_only
                ]:
                    cmds = module.get_cmd_list()
                    self.notice(
                        target, " * {0}: {1}".format(module_name, ", ".join(cmds) if len(cmds) > 0 else "No commands")
                    )

        elif False and admin and cmd == "admin_help":
            if len(arglist) > 0:
                for (module_name, module) in self.modules.get_loaded_modules():
                    if module.has_admin_cmd(arglist[0]):
                        self.notice(source, module.get_admin_cmd(arglist[0]).__doc__)
            else:
                self.notice(source, "!admin_help: this help text (send !admin_help <command> for command help")
                self.notice(source, "!die:                                   kill the bot")
                self.notice(source, "!raw:                                   send raw irc command")
                self.notice(source, "!admins:                                see who are admin")
                self.notice(source, "!restart_class:                         restart the main Bot class")
                for (module_name, module) in self.modules.get_loaded_modules():
                    cmds = module.get_admin_cmd_list()
                    if len(cmds) > 0:
                        self.notice(source, " * {0}: {1}".format(module_name, ", ".join(cmds)))
        else:
            for (module_name, module) in self.modules.get_loaded_modules():
                try:
                    if module.has_cmd(cmd):
                        lines = module.get_cmd(cmd)(
                            args=arglist, arglist=arglist, raw_args=raw_args, source=source, target=target, admin=admin
                        )
                        if lines:
                            for line in lines:
                                self.notice(target, line)
                    elif admin and module.has_admin_cmd(cmd):
                        lines = module.get_admin_cmd(cmd)(
                            args=arglist, arglist=arglist, raw_args=raw_args, source=source, target=target, admin=admin
                        )
                        if lines:
                            for line in lines:
                                self.notice(source, line)
                except Exception as e:
                    logging.exception("Module '{0}' handle error: {1}".format(module_name, e))