Web   ·   Wiki   ·   Activities   ·   Blog   ·   Lists   ·   Chat   ·   Meeting   ·   Bugs   ·   Git   ·   Translate   ·   Archive   ·   People   ·   Donate
summaryrefslogtreecommitdiffstats
path: root/services/console/lib/purk/scripts/irc_script.py
diff options
context:
space:
mode:
Diffstat (limited to 'services/console/lib/purk/scripts/irc_script.py')
-rw-r--r--services/console/lib/purk/scripts/irc_script.py588
1 files changed, 0 insertions, 588 deletions
diff --git a/services/console/lib/purk/scripts/irc_script.py b/services/console/lib/purk/scripts/irc_script.py
deleted file mode 100644
index 4582d72..0000000
--- a/services/console/lib/purk/scripts/irc_script.py
+++ /dev/null
@@ -1,588 +0,0 @@
-import time
-
-from conf import conf
-import ui
-import windows
-import irc
-
-COMMAND_PREFIX = conf.get('command_prefix', '/')
-
-NICK_SUFFIX = r"`_-\|0123456789"
-
-_hextochr = dict(('%02x' % i, chr(i)) for i in range(256))
-def unquote(url, rurl=""):
-
- while '%' in url:
- url, char = url.rsplit('%', 1)
-
- chars = char[:2].lower()
-
- if chars in _hextochr:
- rurl = '%s%s%s' % (_hextochr[chars], char[2:], rurl)
- else:
- rurl = "%s%s%s" % ('%', char, rurl)
-
- return url + rurl
-
-#for getting a list of alternative nicks to try on a network
-def _nick_generator(network):
- for nick in network.nicks[1:]:
- yield nick
- if network._nick_error:
- nick = 'ircperson'
- else:
- nick = network.nicks[0]
- import itertools
- for i in itertools.count(1):
- for j in xrange(len(NICK_SUFFIX)**i):
- suffix = ''.join(NICK_SUFFIX[(j/(len(NICK_SUFFIX)**x))%len(NICK_SUFFIX)] for x in xrange(i))
- if network._nick_max_length:
- yield nick[0:network._nick_max_length-i]+suffix
- else:
- yield nick+suffix
-
-def setdownRaw(e):
- if not e.done:
- if not e.network.got_nick:
- if e.msg[1] in ('432','433','436','437'): #nickname unavailable
- failednick = e.msg[3]
- nicks = list(e.network.nicks)
-
- if hasattr(e.network,'_nick_generator'):
- if len(failednick) < len(e.network._next_nick):
- e.network._nick_max_length = len(failednick)
- e.network._next_nick = e.network._nick_generator.next()
- e.network.raw('NICK %s' % e.network._next_nick)
- e.network._nick_error |= (e.msg[1] == '432')
- else:
- e.network._nick_error = (e.msg[1] == '432')
- if len(failednick) < len(e.network.nicks[0]):
- e.network._nick_max_length = len(failednick)
- else:
- e.network._nick_max_length = 0
- e.network._nick_generator = _nick_generator(e.network)
- e.network._next_nick = e.network._nick_generator.next()
- e.network.raw('NICK %s' % e.network._next_nick)
-
- elif e.msg[1] == '431': #no nickname given--this shouldn't happen
- pass
-
- elif e.msg[1] == '001':
- e.network.got_nick = True
- if e.network.me != e.msg[2]:
- core.events.trigger(
- 'Nick', network=e.network, window=e.window,
- source=e.network.me, target=e.msg[2], address='',
- text=e.msg[2]
- )
- e.network.me = e.msg[2]
- if hasattr(e.network,'_nick_generator'):
- del e.network._nick_generator, e.network._nick_max_length, e.network._next_nick
-
- if e.msg[1] == "PING":
- e.network.raw("PONG :%s" % e.msg[-1])
- e.done = True
-
- elif e.msg[1] == "JOIN":
- e.channel = e.target
- e.requested = e.network.norm_case(e.channel) in e.network.requested_joins
- core.events.trigger("Join", e)
- e.done = True
-
- elif e.msg[1] == "PART":
- e.channel = e.target
- e.requested = e.network.norm_case(e.channel) in e.network.requested_parts
- e.text = ' '.join(e.msg[3:])
- core.events.trigger("Part", e)
- e.done = True
-
- elif e.msg[1] in "MODE":
- e.channel = e.target
- e.text = ' '.join(e.msg[3:])
- core.events.trigger("Mode", e)
- e.done = True
-
- elif e.msg[1] == "QUIT":
- core.events.trigger('Quit', e)
- e.done = True
-
- elif e.msg[1] == "KICK":
- e.channel = e.msg[2]
- e.target = e.msg[3]
- core.events.trigger('Kick', e)
- e.done = True
-
- elif e.msg[1] == "NICK":
- core.events.trigger('Nick', e)
- if e.network.me == e.source:
- e.network.me = e.target
-
- e.done = True
-
- elif e.msg[1] == "PRIVMSG":
- core.events.trigger('Text', e)
- e.done = True
-
- elif e.msg[1] == "NOTICE":
- core.events.trigger('Notice', e)
- e.done = True
-
- elif e.msg[1] == "TOPIC":
- core.events.trigger('Topic', e)
- e.done = True
-
- elif e.msg[1] in ("376", "422"): #RPL_ENDOFMOTD
- if e.network.status == irc.INITIALIZING:
- e.network.status = irc.CONNECTED
- core.events.trigger('Connect', e)
- e.done = True
-
- elif e.msg[1] == "470": #forwarded from channel X to channel Y
- if e.network.norm_case(e.msg[3]) in e.network.requested_joins:
- e.network.requested_joins.discard(e.network.norm_case(e.msg[3]))
- e.network.requested_joins.add(e.network.norm_case(e.msg[4]))
-
- elif e.msg[1] == "005": #RPL_ISUPPORT
- for arg in e.msg[3:]:
- if ' ' not in arg: #ignore "are supported by this server"
- if '=' in arg:
- name, value = arg.split('=', 1)
- if value.isdigit():
- value = int(value)
- else:
- name, value = arg, ''
-
- #Workaround for broken servers (bahamut on EnterTheGame)
- if name == 'PREFIX' and value[0] != '(':
- continue
-
- #in theory, we're supposed to replace \xHH with the
- # corresponding ascii character, but I don't think anyone
- # really does this
- e.network.isupport[name] = value
-
- if name == 'PREFIX':
- new_prefixes = {}
- modes, prefixes = value[1:].split(')')
- for mode, prefix in zip(modes, prefixes):
- new_prefixes[mode] = prefix
- new_prefixes[prefix] = mode
- e.network.prefixes = new_prefixes
-
-def setupSocketConnect(e):
- e.network.got_nick = False
- e.network.isupport = {
- 'NETWORK': e.network.server,
- 'PREFIX': '(ohv)@%+',
- 'CHANMODES': 'b,k,l,imnpstr',
- }
- e.network.prefixes = {'o':'@', 'h':'%', 'v':'+', '@':'o', '%':'h', '+':'v'}
- e.network.connect_timestamp = time.time()
- e.network.requested_joins.clear()
- e.network.requested_parts.clear()
- e.network.on_channels.clear()
- if hasattr(e.network,'_nick_generator'):
- del e.network._nick_generator, e.network._nick_max_length, e.network._next_nick
- if not e.done:
- #this needs to be tested--anyone have a server that uses PASS?
- if e.network.password:
- e.network.raw("PASS :%s" % e.network.password)
- e.network.raw("NICK %s" % e.network.nicks[0])
- e.network.raw("USER %s %s %s :%s" %
- (e.network.username, "8", "*", e.network.fullname))
- #per rfc2812 these are username, user mode flags, unused, realname
-
- #e.network.me = None
- e.done = True
-
-def onDisconnect(e):
- if hasattr(e.network,'_reconnect_source'):
- e.network._reconnect_source.unregister()
- del e.network._reconnect_source
- if hasattr(e.network,'connect_timestamp'):
- if e.error and conf.get('autoreconnect',True):
- delay = time.time() - e.network.connect_timestamp > 30 and 30 or 120
- def do_reconnect():
- if not e.network.status:
- server(network=e.network)
- def do_announce_reconnect():
- if not e.network.status:
- windows.get_default(e.network).write("* Will reconnect in %s seconds.." % delay)
- e.network._reconnect_source = ui.register_timer(delay*1000,do_reconnect)
- e.network._reconnect_source = ui.register_idle(do_announce_reconnect)
-
-def onCloseNetwork(e):
- e.network.quit()
- if hasattr(e.network,'_reconnect_source'):
- e.network._reconnect_source.unregister()
- del e.network._reconnect_source
-
-def setdownDisconnect(e):
- if hasattr(e.network,'connect_timestamp'):
- del e.network.connect_timestamp
-
-def setupInput(e):
- if not e.done:
- if e.text.startswith(COMMAND_PREFIX) and not e.ctrl:
- command = e.text[len(COMMAND_PREFIX):]
- else:
- command = 'say - %s' % e.text
-
- core.events.run(command, e.window, e.network)
-
- e.done = True
-
-def onCommandSay(e):
- if isinstance(e.window, windows.ChannelWindow) or isinstance(e.window, windows.QueryWindow):
- e.network.msg(e.window.id, ' '.join(e.args))
- else:
- raise core.events.CommandError("There's no one here to speak to.")
-
-def onCommandMsg(e):
- e.network.msg(e.args[0], ' '.join(e.args[1:]))
-
-def onCommandNotice(e):
- e.network.notice(e.args[0], ' '.join(e.args[1:]))
-
-def onCommandQuery(e):
- windows.new(windows.QueryWindow, e.network, e.args[0], core).activate()
- if len(e.args) > 1:
- message = ' '.join(e.args[1:])
- if message: #this is false if you do "/query nickname "
- e.network.msg(e.args[0], ' '.join(e.args[1:]))
-
-def setupJoin(e):
- if e.source == e.network.me:
- chan = e.network.norm_case(e.channel)
- e.network.on_channels.add(chan)
- e.network.requested_joins.discard(chan)
-
-def setdownPart(e):
- if e.source == e.network.me:
- chan = e.network.norm_case(e.channel)
- e.network.on_channels.discard(chan)
- e.network.requested_parts.discard(chan)
-
-def setdownKick(e):
- if e.target == e.network.me:
- chan = e.network.norm_case(e.channel)
- e.network.on_channels.discard(chan)
-
-def ischan(network, channel):
- return network.norm_case(channel) in network.on_channels
-
-# make /nick work offline
-def change_nick(network, nick):
- if not network.status:
- core.events.trigger(
- 'Nick',
- network=network, window=windows.get_default(network),
- source=network.me, target=nick, address='', text=nick
- )
- network.nicks[0] = nick
- network.me = nick
- else:
- network.raw('NICK :%s' % nick)
-
-def onCommandNick(e):
- default_nick = irc.default_nicks()[0]
- if 't' not in e.switches and e.network.me == default_nick:
- conf['nick'] = e.args[0]
- import conf as _conf
- _conf.save()
- for network in set(w.network for w in core.manager):
- if network.me == default_nick:
- change_nick(network, e.args[0])
- else:
- change_nick(e.network, e.args[0])
-
-def setdownNick(e):
- if e.source != e.network.me:
- window = windows.get(windows.QueryWindow, e.network, e.source)
- if window:
- window.id = e.target
-
-# make /quit always disconnect us
-def onCommandQuit(e):
- if e.network.status:
- e.network.quit(' '.join(e.args))
- else:
- raise core.events.CommandError("We're not connected to a network.")
-
-def onCommandRaw(e):
- if e.network.status >= irc.INITIALIZING:
- e.network.raw(' '.join(e.args))
- else:
- raise core.events.CommandError("We're not connected to a network.")
-
-onCommandQuote = onCommandRaw
-
-def onCommandJoin(e):
- if e.args:
- if e.network.status >= irc.INITIALIZING:
- e.network.join(' '.join(e.args), requested = 'n' not in e.switches)
- else:
- raise core.events.CommandError("We're not connected.")
- elif isinstance(e.window, windows.ChannelWindow):
- e.window.network.join(e.window.id, requested = 'n' not in e.switches)
- else:
- raise core.events.CommandError("You must supply a channel.")
-
-def onCommandPart(e):
- if e.args:
- if e.network.status >= irc.INITIALIZING:
- e.network.part(' '.join(e.args), requested = 'n' not in e.switches)
- else:
- raise core.events.CommandError("We're not connected.")
- elif isinstance(e.window, windows.ChannelWindow):
- e.window.network.part(e.window.id, requested = 'n' not in e.switches)
- else:
- raise core.events.CommandError("You must supply a channel.")
-
-def onCommandHop(e):
- if e.args:
- if e.network.status >= irc.INITIALIZING:
- e.network.part(e.args[0], requested = False)
- e.network.join(' '.join(e.args), requested = False)
- else:
- raise core.events.CommandError("We're not connected.")
- elif isinstance(e.window, windows.ChannelWindow):
- e.window.network.part(e.window.id, requested = False)
- e.window.network.join(e.window.id, requested = False)
- else:
- raise core.events.CommandError("You must supply a channel.")
-
-#this should be used whereever a new irc.Network may need to be created
-def server(server=None,port=6667,network=None,connect=True):
- network_info = {}
-
- if server:
- network_info["name"] = server
- network_info["server"] = server
- if port:
- network_info["port"] = port
- get_network_info(server, network_info)
-
- if not network:
- network = irc.Network(**network_info)
- windows.new(windows.StatusWindow, network, "status").activate()
- else:
- if "server" in network_info:
- network.name = network_info['name']
- network.server = network_info['server']
- if not network.status:
- #window = windows.get_default(network)
- window = core.window
- if window:
- window.update()
- if "port" in network_info:
- network.port = network_info["port"]
-
- if network.status:
- network.quit()
- if connect:
- network.connect()
- core.window.write("* Connecting to %s on port %s" % (network.server, network.port))
- #windows.get_default(network).write(
- # "* Connecting to %s on port %s" % (network.server, network.port)
- # )
-
- return network
-
-def onCommandServer(e):
- host = port = None
-
- if e.args:
- host = e.args[0]
-
- if ':' in host:
- host, port = host.rsplit(':', 1)
- port = int(port)
-
- elif len(e.args) > 1:
- port = int(e.args[1])
-
- else:
- port = 6667
-
- if 'm' in e.switches:
- network = None
- else:
- network = e.network
-
- server(server=host, port=port, network=network, connect='o' not in e.switches)
-
-#see http://www.w3.org/Addressing/draft-mirashi-url-irc-01.txt
-def onCommandIrcurl(e):
- url = e.args[0]
-
- if url.startswith('irc://'):
- url = url[6:]
-
- if not url.startswith('/'):
- host, target = url.rsplit('/',1)
- if ':' in host:
- host, port = host.rsplit(':',1)
- else:
- port = 6667
- else:
- host = None
- port = 6667
- target = url
-
- if host:
- if e.network and e.network.server == host:
- network = e.network
- else:
- for w in list(windows.manager):
- if w.network and w.network.server == host:
- network = w.network
- break
- else:
- for w in list(windows.manager):
- if w.network and w.network.server == 'irc.default.org':
- network = server(host,port,w.network)
- break
- else:
- network = server(host,port)
-
- if ',' in target:
- target, modifiers = target.split(',',1)
- action = ''
- else:
- target = unquote(target)
- if target[0] not in '#&+':
- target = '#'+target
- action = 'join %s' % target
-
- if network.status == irc.CONNECTED:
- core.events.run(action, windows.get_default(network), network)
- else:
- if not hasattr(network,'temp_perform'):
- network.temp_perform = [action]
- else:
- network.temp_perform.append(action)
-
-#commands that we need to add a : to but otherwise can send unchanged
-#the dictionary contains the number of arguments we take without adding the :
-trailing = {
- 'away':0,
- 'cnotice':2,
- 'cprivmsg':2,
- 'kick':2,
- 'kill':1,
- 'part':1,
- 'squery':1,
- 'squit':1,
- 'topic':1,
- 'wallops':0,
- }
-
-needschan = {
- 'topic':0,
- 'invite':1,
- 'kick':0,
-# 'mode':0, #this is commonly used for channels, but can apply to users
-# 'names':0, #with no parameters, this is supposed to give a list of all users; we may be able to safely ignore that.
- }
-
-def setupCommand(e):
- if not e.done:
- if e.name in needschan and isinstance(e.window, windows.ChannelWindow):
- valid_chan_prefixes = e.network.isupport.get('CHANTYPES', '#&+')
- chan_pos = needschan[e.name]
-
- if len(e.args) > chan_pos:
- if not e.args[chan_pos] or e.args[chan_pos][0] not in valid_chan_prefixes:
- e.args.insert(chan_pos, e.window.id)
- else:
- e.args.append(e.window.id)
-
- if e.name in trailing:
- trailing_pos = trailing[e.name]
-
- if len(e.args) > trailing_pos:
- e.args[trailing_pos] = ':%s' % e.args[trailing_pos]
-
- e.text = '%s %s' % (e.name, ' '.join(e.args))
-
-def setdownCommand(e):
- if not e.done and e.network.status >= irc.INITIALIZING:
- e.network.raw(e.text)
- e.done = True
-
-def get_network_info(name, network_info):
- conf_info = conf.get('networks', {}).get(name)
-
- if conf_info:
- network_info['server'] = name
- network_info.update(conf_info)
-
-def onStart(e):
- for network in conf.get('start_networks', []):
- server(server=network)
-
-def onConnect(e):
- network_info = conf.get('networks', {}).get(e.network.name, {})
-
- for command in network_info.get('perform', []):
- while command.startswith(COMMAND_PREFIX):
- command = command[len(COMMAND_PREFIX):]
- core.events.run(command, e.window, e.network)
-
- tojoin = ','.join(network_info.get('join', []))
- if tojoin:
- core.events.run('join -n %s' % tojoin, e.window, e.network)
-
- if hasattr(e.network,'temp_perform'):
- for command in e.network.temp_perform:
- core.events.run(command, e.window, e.network)
- del e.network.temp_perform
-
-def isautojoin(network, channel):
- try:
- joinlist = conf['networks'][network.name]['join']
- except KeyError:
- return False
- normchannel = network.norm_case(channel)
- for chan in joinlist:
- if normchannel == network.norm_case(chan):
- return True
- return False
-
-def setautojoin(network, channel):
- if 'networks' not in conf:
- conf['networks'] = networks = {}
- else:
- networks = conf['networks']
- if network.name not in networks:
- networks[network.name] = network_settings = {}
- if 'start_networks' not in conf:
- conf['start_networks'] = []
- conf['start_networks'].append(network.name)
- else:
- network_settings = networks[network.name]
-
- if 'join' not in network_settings:
- network_settings['join'] = [channel]
- else:
- network_settings['join'].append(channel)
-
-def unsetautojoin(network, channel):
- try:
- joinlist = conf['networks'][network.name]['join']
- except KeyError:
- return False
- normchannel = network.norm_case(channel)
- for i, chan in enumerate(joinlist[:]):
- if normchannel == network.norm_case(chan):
- joinlist.pop(i)
-
-def onChannelMenu(e):
- def toggle_join():
- if isautojoin(e.network, e.channel):
- unsetautojoin(e.network, e.channel)
- else:
- setautojoin(e.network, e.channel)
-
- e.menu.append(('Autojoin', isautojoin(e.network, e.channel), toggle_join))