class Plugin(BasePlugin): """ a plugin to do simple substitution """ def __init__(self, *args, **kwargs): """ initialize the instance """ BasePlugin.__init__(self, *args, **kwargs) self.savesubfile = os.path.join(self.savedir, 'subs.txt') self._substitutes = PersistentDict(self.savesubfile, 'c') def load(self): """ load the plugins """ BasePlugin.load(self) parser = argp.ArgumentParser(add_help=False, description='add a simple substitute') parser.add_argument('original', help='the output to substitute', default='', nargs='?') parser.add_argument('replacement', help='the string to replace it with', default='', nargs='?') self.api('commands.add')('add', self.cmd_add, parser=parser) parser = argp.ArgumentParser(add_help=False, description='remove a substitute') parser.add_argument('substitute', help='the substitute to remove', default='', nargs='?') self.api('commands.add')('remove', self.cmd_remove, parser=parser) parser = argp.ArgumentParser(add_help=False, description='list substitutes') parser.add_argument('match', help='list only substitutes that have this argument in them', default='', nargs='?') self.api('commands.add')('list', self.cmd_list, parser=parser) parser = argp.ArgumentParser(add_help=False, description='clear all substitutes') self.api('commands.add')('clear', self.cmd_clear, parser=parser) self.api('commands.default')('list') self.api('events.register')('from_mud_event', self.findsub) self.api('events.register')('plugin_%s_savestate' % self.sname, self._savestate) def findsub(self, args): """ this function finds subs in mud data """ data = args['original'] dtype = args['dtype'] if dtype != 'fromproxy': for mem in self._substitutes.keys(): if mem in data: ndata = data.replace(mem, self.api('colors.convertcolors')( self._substitutes[mem]['sub'])) if ndata != data: args['trace']['changes'].append({'flag':'Modify', 'data':'changed "%s" to "%s"' % \ (data, ndata), 'plugin':self.sname, 'eventname':args['eventname']}) data = ndata args['original'] = data return args def cmd_add(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Add a substitute @CUsage@w: add @Y<originalstring>@w @M<replacementstring>@w @Yoriginalstring@w = The original string to be replaced @Mreplacementstring@w = The new string """ tmsg = [] if args['original'] and args['replacement']: tmsg.append("@GAdding substitute@w : '%s' will be replaced by '%s'" % \ (args['original'], args['replacement'])) self.addsub(args['original'], args['replacement']) return True, tmsg tmsg.append("@RPlease specify all arguments@w") return False, tmsg def cmd_remove(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Remove a substitute @CUsage@w: rem @Y<originalstring>@w @Yoriginalstring@w = The original string """ tmsg = [] if args['substitute']: tmsg.append("@GRemoving substitute@w : '%s'" % (args['substitute'])) self.removesub(args['substitute']) return True, tmsg return False, tmsg def cmd_list(self, args): """ @G%(name)s@w - @B%(cmdname)s@w List substitutes @CUsage@w: list """ tmsg = self.listsubs(args['match']) return True, tmsg def cmd_clear(self, args): # pylint: disable=unused-argument """ @G%(name)s@w - @B%(cmdname)s@w List substitutes @CUsage@w: list""" self.clearsubs() return True, ['Substitutes cleared'] def addsub(self, item, sub): """ internally add a substitute """ self._substitutes[item] = {'sub':sub} self._substitutes.sync() def removesub(self, item): """ internally remove a substitute """ if item in self._substitutes: del self._substitutes[item] self._substitutes.sync() def listsubs(self, match): """ return a table of strings that list subs """ tmsg = [] for item in self._substitutes: if not match or match in item: tmsg.append("%-35s : %s@w" % (item, self._substitutes[item]['sub'])) if not tmsg: tmsg = ['None'] return tmsg def clearsubs(self): """ clear all subs """ self._substitutes.clear() self._substitutes.sync() def reset(self): """ reset the plugin """ BasePlugin.reset(self) self.clearsubs() def _savestate(self, _=None): """ save states """ self._substitutes.sync()
class Plugin(BasePlugin): """ a plugin for user actions """ def __init__(self, *args, **kwargs): """ initialize the instance """ BasePlugin.__init__(self, *args, **kwargs) self.canreload = True self.regexlookup = {} self.actiongroups = {} self.compiledregex = {} self.sessionhits = {} self.saveactionsfile = os.path.join(self.savedir, 'actions.txt') self.actions = PersistentDict(self.saveactionsfile, 'c') for i in self.actions: self.compiledregex[i] = re.compile(self.actions[i]['regex']) def load(self): """ load the plugin """ BasePlugin.load(self) self.api.get('setting.add')('nextnum', 0, int, 'the number of the next action added', readonly=True) parser = argparse.ArgumentParser(add_help=False, description='add a action') parser.add_argument('regex', help='the regex to match', default='', nargs='?') parser.add_argument('action', help='the action to take', default='', nargs='?') parser.add_argument('send', help='where to send the action', default='execute', nargs='?', choices=self.api.get('api.getchildren')('send')) parser.add_argument('-c', "--color", help="match colors (@@colors)", action="store_true") parser.add_argument('-d', "--disable", help="disable the action", action="store_true") parser.add_argument('-g', "--group", help="the action group", default="") parser.add_argument('-o', "--overwrite", help="overwrite an action if it already exists", action="store_true") self.api.get('commands.add')('add', self.cmd_add, parser=parser) parser = argparse.ArgumentParser(add_help=False, description='list actions') parser.add_argument( 'match', help='list only actions that have this argument in them', default='', nargs='?') self.api.get('commands.add')('list', self.cmd_list, parser=parser) parser = argparse.ArgumentParser(add_help=False, description='remove an action') parser.add_argument('action', help='the action to remove', default='', nargs='?') self.api.get('commands.add')('remove', self.cmd_remove, parser=parser) parser = argparse.ArgumentParser(add_help=False, description='toggle enabled flag') parser.add_argument('action', help='the action to toggle', default='', nargs='?') self.api.get('commands.add')('toggle', self.cmd_toggle, parser=parser) parser = argparse.ArgumentParser( add_help=False, description='get detail for an action') parser.add_argument('action', help='the action to get details for', default='', nargs='?') self.api.get('commands.add')('detail', self.cmd_detail, parser=parser) parser = argparse.ArgumentParser( add_help=False, description='toggle all actions in a group') parser.add_argument('group', help='the group to toggle', default='', nargs='?') parser.add_argument('-d', "--disable", help="disable the group", action="store_true") self.api.get('commands.add')('groupt', self.cmd_grouptoggle, parser=parser) #self.api.get('commands.add')('stats', self.cmd_stats, # shelp='show action stats') self.api.get('events.register')('from_mud_event', self.checkactions, prio=5) # self.api.get('events.register')('plugin_stats', self.getpluginstats) def lookup_action(self, action): """ lookup an action by number or name """ nitem = None try: num = int(action) nitem = None for titem in self.actions.keys(): if num == self.actions[titem]['num']: nitem = titem break except ValueError: if action in self.actions: nitem = action return nitem @timeit def checkactions(self, args): """ check a line of text from the mud the is called whenever the from_mud_event is raised """ data = args['noansi'] colordata = args['convertansi'] for i in self.actions: if self.actions[i]['enabled']: trigre = self.compiledregex[i] datatomatch = data if 'matchcolor' in self.actions[i] and \ self.actions[i]['matchcolor']: datatomatch = colordata mat = trigre.match(datatomatch) self.api.get('send.msg')('attempting to match %s' % datatomatch) if mat: if i in self.sessionhits: self.sessionhits[i] = 0 self.sessionhits[i] = self.sessionhits[i] + 1 if 'hits' in self.actions[i]: self.actions[i]['hits'] = 0 self.actions[i]['hits'] = self.actions[i]['hits'] + 1 self.api.get('send.msg')('matched line: %s to action %s' % (data, i)) templ = Template(self.actions[i]['action']) newaction = templ.safe_substitute(mat.groupdict()) sendtype = 'send.' + self.actions[i]['send'] self.api.get('send.msg')('sent %s to %s' % (newaction, sendtype)) self.api.get(sendtype)(newaction) return args def cmd_add(self, args): """ add user defined actions """ if not args['regex']: return False, ['Please include a regex'] if not args['action']: return False, ['Please include an action'] if not args['overwrite'] and args['regex'] in self.actions: return True, ['Action: %s already exists.' % args['regex']] else: num = 0 if args['regex'] in self.actions: num = self.actions[args['regex']]['num'] else: num = self.api.get('setting.gets')('nextnum') self.api.get('setting.change')('nextnum', num + 1) self.actions[args['regex']] = { 'num': num, 'regex': args['regex'], 'action': args['action'], 'send': args['send'], 'matchcolor': args['color'], 'enabled': not args['disable'], 'group': args['group'] } self.actions.sync() self.compiledregex[args['regex']] = re.compile(args['regex']) return True, ['added action %s - regex: %s' % (num, args['regex'])] return False, ['You should never see this'] def cmd_remove(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Remove an action @CUsage@w: rem @Y<originalstring>@w @Yoriginalstring@w = The original string """ tmsg = [] if args['action']: retval = self.removeaction(args['action']) if retval: tmsg.append("@GRemoving action@w : '%s'" % (retval)) else: tmsg.append("@GCould not remove action@w : '%s'" % (args['action'])) return True, tmsg else: return False, ['@RPlease include an action to remove@w'] def cmd_list(self, args): """ @G%(name)s@w - @B%(cmdname)s@w List actiones @CUsage@w: list """ tmsg = self.listactions(args['match']) return True, tmsg def cmd_toggle(self, args): """ toggle the enabled flag """ tmsg = [] if args['action']: retval = self.toggleaction(args['action']) if retval: if self.actions[retval]['enabled']: tmsg.append("@GEnabled action@w : '%s'" % (retval)) else: tmsg.append("@GDisabled action@w : '%s'" % (retval)) else: tmsg.append("@GDoes not exist@w : '%s'" % (args['action'])) return True, tmsg else: return False, ['@RPlease include an action to toggle@w'] def cmd_grouptoggle(self, args): """ toggle all actions in a group """ tmsg = [] togglea = [] state = not args['disable'] if args['group']: for i in self.actions: if self.actions[i]['group'] == args['group']: self.actions[i]['enabled'] = state togglea.append('%s' % self.actions[i]['num']) if togglea: tmsg.append('The following actions were %s: %s' % \ ('enabled' if state else 'disabled', ','.join(togglea))) else: tmsg.append('No actions were modified') return True, tmsg else: return False, ['@RPlease include a group to toggle@w'] def cmd_detail(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Add a action @CUsage@w: add @Y<originalstring>@w @M<replacementstring>@w @Yoriginalstring@w = The original string to be replaced @Mreplacementstring@w = The new string """ tmsg = [] if args['action']: action = self.lookup_action(args['action']) if action: if 'hits' in self.actions[action]: self.actions[action]['hits'] = 0 if action in self.sessionhits: self.sessionhits[action] = 0 tmsg.append('%-12s : %d' % ('Num', self.actions[action]['num'])) tmsg.append('%-12s : %s' % \ ('Enabled', 'Y' if self.actions[action]['enabled'] else 'N')) tmsg.append('%-12s : %d' % ('Total Hits', self.actions[action]['hits'])) tmsg.append('%-12s : %d' % ('Session Hits', self.sessionhits[action])) tmsg.append('%-12s : %s' % ('Regex', self.actions[action]['regex'])) tmsg.append('%-12s : %s' % ('Action', self.actions[action]['action'])) tmsg.append('%-12s : %s' % ('Group', self.actions[action]['group'])) tmsg.append( '%-12s : %s' % ('Match Color', self.actions[action]['matchcolor'])) else: return True, [ '@RAction does not exits@w : \'%s\'' % (args['action']) ] return True, tmsg else: return False, ['@RPlease include all arguments@w'] def listactions(self, match): """ return a table of strings that list actiones """ tmsg = [] for action in sorted(self.actions.keys()): item = self.actions[action] if not match or match in item: regex = self.api.get('colors.stripansi')(item['regex']) if len(regex) > 30: regex = regex[:27] + '...' action = self.api.get('colors.stripansi')(item['action']) if len(action) > 30: action = action[:27] + '...' tmsg.append("%4s %2s %-10s %-32s : %s@w" % \ (item['num'], 'Y' if item['enabled'] else 'N', item['group'], regex, action)) if len(tmsg) == 0: tmsg = ['None'] else: tmsg.insert( 0, "%4s %2s %-10s %-32s : %s@w" % ('#', 'E', 'Group', 'Regex', 'Action')) tmsg.insert(1, '@B' + '-' * 60 + '@w') return tmsg def removeaction(self, item): """ internally remove a action """ action = self.lookup_action(item) print 'lookup_action', item, 'returned', action if action >= 0: del self.actions[action] self.actions.sync() return action def toggleaction(self, item): """ toggle an action """ action = self.lookup_action(item) if action: self.actions[action][ 'enabled'] = not self.actions[action]['enabled'] return action def clearactions(self): """ clear all actiones """ self.actions.clear() self.actions.sync() def reset(self): """ reset the plugin """ BasePlugin.reset(self) self.clearactions() def savestate(self): """ save states """ BasePlugin.savestate(self) self.actions.sync()
class Plugin(BasePlugin): """ a plugin for user actions """ def __init__(self, *args, **kwargs): """ initialize the instance """ BasePlugin.__init__(self, *args, **kwargs) self.canreload = True self.regexlookup = {} self.actiongroups = {} self.compiledregex = {} self.sessionhits = {} self.saveactionsfile = os.path.join(self.savedir, 'actions.txt') self.actions = PersistentDict(self.saveactionsfile, 'c') def load(self): """ load the plugin """ BasePlugin.load(self) self.api('setting.add')('nextnum', 0, int, 'the number of the next action added', readonly=True) parser = argp.ArgumentParser(add_help=False, description='add a action') parser.add_argument('regex', help='the regex to match', default='', nargs='?') parser.add_argument('action', help='the action to take', default='', nargs='?') parser.add_argument('send', help='where to send the action', default='execute', nargs='?', choices=self.api('api.getchildren')('send')) parser.add_argument('-c', "--color", help="match colors (@@colors)", action="store_true") parser.add_argument('-d', "--disable", help="disable the action", action="store_true") parser.add_argument('-g', "--group", help="the action group", default="") parser.add_argument('-o', "--overwrite", help="overwrite an action if it already exists", action="store_true") self.api('commands.add')('add', self.cmd_add, parser=parser) parser = argp.ArgumentParser(add_help=False, description='list actions') parser.add_argument('match', help='list only actions that have this argument in them', default='', nargs='?') self.api('commands.add')('list', self.cmd_list, parser=parser) parser = argp.ArgumentParser(add_help=False, description='remove an action') parser.add_argument('action', help='the action to remove', default='', nargs='?') self.api('commands.add')('remove', self.cmd_remove, parser=parser) parser = argp.ArgumentParser(add_help=False, description='toggle enabled flag') parser.add_argument('action', help='the action to toggle', default='', nargs='?') action = parser.add_mutually_exclusive_group() action.add_argument('-t', '--toggle', action='store_const', dest='togact', const='toggle', default='toggle', help='toggle the action') action.add_argument('-d', '--disable', action='store_const', dest='togact', const='disable', help='disable the action') action.add_argument('-e', '--enable', action='store_const', dest='togact', const='enable', help='enable the action') self.api('commands.add')('toggle', self.cmd_toggle, parser=parser) parser = argp.ArgumentParser(add_help=False, description='get detail for an action') parser.add_argument('action', help='the action to get details for', default='', nargs='?') self.api('commands.add')('detail', self.cmd_detail, parser=parser) parser = argp.ArgumentParser(add_help=False, description='toggle all actions in a group') parser.add_argument('group', help='the group to toggle', default='', nargs='?') action = parser.add_mutually_exclusive_group() action.add_argument('-t', '--toggle', action='store_const', dest='togact', const='toggle', default='toggle', help='toggle the action') action.add_argument('-d', '--disable', action='store_const', dest='togact', const='disable', help='disable the action') action.add_argument('-e', '--enable', action='store_const', dest='togact', const='enable', help='enable the action') self.api('commands.add')('groupt', self.cmd_grouptoggle, parser=parser) for action in self.actions.values(): self.register_action(action) self.api('events.register')('plugin_%s_savestate' % self.sname, self._savestate) def register_action(self, action): """ register an action as a trigger """ if 'triggername' not in action: action['triggername'] = "action_%s" % action['num'] self.api('triggers.add')(action['triggername'], action['regex']) self.api('events.register')('trigger_%s' % action['triggername'], self.action_matched) def unregister_action(self, action): """ unregister an action """ self.api('events.unregister')('trigger_%s' % action['triggername'], self.action_matched) self.api('triggers.remove')(action['triggername']) def action_matched(self, args): """ do something when an action is matched """ actionnum = int(args['triggername'].split('_')[-1]) action = self.lookup_action(actionnum) if action: akey = action['regex'] if akey not in self.sessionhits: self.sessionhits[akey] = 0 self.sessionhits[akey] = self.sessionhits[akey] + 1 action['hits'] = action['hits'] + 1 self.api('send.msg')('matched line: %s to action %s' % (args['line'], akey)) templ = Template(action['action']) newaction = templ.safe_substitute(args) sendtype = 'send.' + action['send'] self.api('send.msg')('sent %s to %s' % (newaction, sendtype)) self.api(sendtype)(newaction) else: self.api('send.error')("Bug: could not find action for trigger %s" % \ args['triggername']) def lookup_action(self, action): """ lookup an action by number or name """ nitem = None try: num = int(action) nitem = None for titem in self.actions.keys(): if num == self.actions[titem]['num']: nitem = self.actions[titem] break except ValueError: if action in self.actions: nitem = action return nitem def cmd_add(self, args): """ add user defined actions """ if not args['regex']: return False, ['Please include a regex'] if not args['action']: return False, ['Please include an action'] if not args['overwrite'] and args['regex'] in self.actions: return True, ['Action: %s already exists.' % args['regex']] else: num = 0 if args['regex'] in self.actions: num = self.actions[args['regex']]['num'] else: num = self.api('setting.gets')('nextnum') self.api('setting.change')('nextnum', num + 1) self.actions[args['regex']] = { 'num':num, 'hits':0, 'regex': args['regex'], 'action':args['action'], 'send':args['send'], 'matchcolor':args['color'], 'enabled':not args['disable'], 'group':args['group'], 'triggername':"action_%s" % num } self.actions.sync() self.register_action(self.actions[args['regex']]) return True, ['added action %s - regex: %s' % (num, args['regex'])] return False, ['You should never see this'] def cmd_remove(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Remove an action @CUsage@w: rem @Y<originalstring>@w @Yoriginalstring@w = The original string """ tmsg = [] if args['action']: retval = self.removeaction(args['action']) if retval: tmsg.append("@GRemoving action@w : '%s'" % (retval)) else: tmsg.append("@GCould not remove action@w : '%s'" % (args['action'])) return True, tmsg else: return False, ['@RPlease include an action to remove@w'] def cmd_list(self, args): """ @G%(name)s@w - @B%(cmdname)s@w List actiones @CUsage@w: list """ tmsg = self.listactions(args['match']) return True, tmsg def cmd_toggle(self, args): """ toggle the enabled flag """ tmsg = [] if args['togact'] == 'disable': state = False elif args['togact'] == 'enable': state = True else: state = "toggle" if args['action']: action = self.toggleaction(args['action'], flag=state) if action: if action['enabled']: tmsg.append("@GEnabled action@w : '%s'" % (action['num'])) else: tmsg.append("@GDisabled action@w : '%s'" % (action['num'])) else: tmsg.append("@GDoes not exist@w : '%s'" % (args['action'])) return True, tmsg else: return False, ['@RPlease include an action to toggle@w'] def cmd_grouptoggle(self, args): """ toggle all actions in a group """ tmsg = [] togglea = [] if args['togact'] == 'disable': state = False elif args['togact'] == 'enable': state = True else: state = "toggle" if args['group']: for i in self.actions: if self.actions[i]['group'] == args['group']: self.toggleaction(self.actions[i]['num'], flag=state) togglea.append('%s' % self.actions[i]['num']) if togglea: tmsg.append('The following actions were %s: %s' % \ ('enabled' if state else 'disabled', ','.join(togglea))) else: tmsg.append('No actions were modified') return True, tmsg else: return False, ['@RPlease include a group to toggle@w'] def cmd_detail(self, args): """ @G%(name)s@w - @B%(cmdname)s@w get details of an action @CUsage@w: detail 1 @Yaction@w = the action to get details, either the number or regex """ tmsg = [] if args['action']: action = self.lookup_action(args['action']) if action: if 'hits' not in action: action['hits'] = 0 if action['regex'] not in self.sessionhits: self.sessionhits[action['regex']] = 0 tmsg.append('%-12s : %d' % ('Num', action['num'])) tmsg.append('%-12s : %s' % \ ('Enabled', 'Y' if action['enabled'] else 'N')) tmsg.append('%-12s : %d' % ('Total Hits', action['hits'])) tmsg.append('%-12s : %d' % ('Session Hits', self.sessionhits[action['regex']])) tmsg.append('%-12s : %s' % ('Regex', action['regex'])) tmsg.append('%-12s : %s' % ('Action', action['action'])) tmsg.append('%-12s : %s' % ('Group', action['group'])) tmsg.append('%-12s : %s' % ('Match Color', action['matchcolor'])) tmsg.append('%-12s : %s' % ('Trigger Name', action['triggername'])) else: return True, ['@RAction does not exist@w : \'%s\'' % (args['action'])] return True, tmsg else: return False, ['@RPlease include all arguments@w'] def listactions(self, match): """ return a table of strings that list actions """ tmsg = [] for action in sorted(self.actions.keys()): item = self.actions[action] if not match or match in item: regex = self.api('colors.stripansi')(item['regex']) if len(regex) > 30: regex = regex[:27] + '...' action = self.api('colors.stripansi')(item['action']) if len(action) > 30: action = action[:27] + '...' tmsg.append("%4s %2s %-10s %-32s : %s@w" % \ (item['num'], 'Y' if item['enabled'] else 'N', item['group'], regex, action)) if not tmsg: tmsg = ['None'] else: tmsg.insert(0, "%4s %2s %-10s %-32s : %s@w" % ('#', 'E', 'Group', 'Regex', 'Action')) tmsg.insert(1, '@B' + '-' * 60 + '@w') return tmsg def removeaction(self, item): """ internally remove a action """ action = self.lookup_action(item) if action and action['regex'] in self.actions: self.unregister_action(action) del self.actions[action['regex']] self.actions.sync() return action def toggleaction(self, item, flag="toggle"): """ toggle an action """ action = self.lookup_action(item) if action: if flag == "toggle": action['enabled'] = not action['enabled'] else: action['enabled'] = bool(flag) if action['enabled']: self.register_action(action) else: self.unregister_action(action) return action def clearactions(self): """ clear all actiones """ for action in self.actions.values(): self.unregister_action(action) self.actions.clear() self.actions.sync() def reset(self): """ reset the plugin """ BasePlugin.reset(self) self.clearactions() def _savestate(self, _=None): """ save states """ self.actions.sync()
class Plugin(BasePlugin): """ a plugin to do simple substitution """ def __init__(self, *args, **kwargs): """ initialize the instance """ BasePlugin.__init__(self, *args, **kwargs) self.savesubfile = os.path.join(self.savedir, 'subs.txt') self._substitutes = PersistentDict(self.savesubfile, 'c') def load(self): """ load the plugins """ BasePlugin.load(self) parser = argp.ArgumentParser(add_help=False, description='add a simple substitute') parser.add_argument('original', help='the output to substitute', default='', nargs='?') parser.add_argument('replacement', help='the string to replace it with', default='', nargs='?') self.api('commands.add')('add', self.cmd_add, parser=parser) parser = argp.ArgumentParser(add_help=False, description='remove a substitute') parser.add_argument('substitute', help='the substitute to remove', default='', nargs='?') self.api('commands.add')('remove', self.cmd_remove, parser=parser) parser = argp.ArgumentParser(add_help=False, description='list substitutes') parser.add_argument( 'match', help='list only substitutes that have this argument in them', default='', nargs='?') self.api('commands.add')('list', self.cmd_list, parser=parser) parser = argp.ArgumentParser(add_help=False, description='clear all substitutes') self.api('commands.add')('clear', self.cmd_clear, parser=parser) self.api('commands.default')('list') self.api('events.register')('from_mud_event', self.findsub) self.api('events.register')('plugin_%s_savestate' % self.sname, self._savestate) def findsub(self, args): """ this function finds subs in mud data """ data = args['original'] dtype = args['dtype'] if dtype != 'fromproxy': for mem in self._substitutes.keys(): if mem in data: ndata = data.replace( mem, self.api('colors.convertcolors')( self._substitutes[mem]['sub'])) if ndata != data: args['trace']['changes'].append({'flag':'Modify', 'data':'changed "%s" to "%s"' % \ (data, ndata), 'plugin':self.sname, 'eventname':args['eventname']}) data = ndata args['original'] = data return args def cmd_add(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Add a substitute @CUsage@w: add @Y<originalstring>@w @M<replacementstring>@w @Yoriginalstring@w = The original string to be replaced @Mreplacementstring@w = The new string """ tmsg = [] if args['original'] and args['replacement']: tmsg.append("@GAdding substitute@w : '%s' will be replaced by '%s'" % \ (args['original'], args['replacement'])) self.addsub(args['original'], args['replacement']) return True, tmsg tmsg.append("@RPlease specify all arguments@w") return False, tmsg def cmd_remove(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Remove a substitute @CUsage@w: rem @Y<originalstring>@w @Yoriginalstring@w = The original string """ tmsg = [] if args['substitute']: tmsg.append("@GRemoving substitute@w : '%s'" % (args['substitute'])) self.removesub(args['substitute']) return True, tmsg return False, tmsg def cmd_list(self, args): """ @G%(name)s@w - @B%(cmdname)s@w List substitutes @CUsage@w: list """ tmsg = self.listsubs(args['match']) return True, tmsg def cmd_clear(self, args): # pylint: disable=unused-argument """ @G%(name)s@w - @B%(cmdname)s@w List substitutes @CUsage@w: list""" self.clearsubs() return True, ['Substitutes cleared'] def addsub(self, item, sub): """ internally add a substitute """ self._substitutes[item] = {'sub': sub} self._substitutes.sync() def removesub(self, item): """ internally remove a substitute """ if item in self._substitutes: del self._substitutes[item] self._substitutes.sync() def listsubs(self, match): """ return a table of strings that list subs """ tmsg = [] for item in self._substitutes: if not match or match in item: tmsg.append("%-35s : %s@w" % (item, self._substitutes[item]['sub'])) if not tmsg: tmsg = ['None'] return tmsg def clearsubs(self): """ clear all subs """ self._substitutes.clear() self._substitutes.sync() def reset(self): """ reset the plugin """ BasePlugin.reset(self) self.clearsubs() def _savestate(self, _=None): """ save states """ self._substitutes.sync()
class Plugin(BasePlugin): """ a plugin to handle user aliases """ def __init__(self, *args, **kwargs): """ initialize the instance """ BasePlugin.__init__(self, *args, **kwargs) self.aliasfile = os.path.join(self.savedir, 'aliases.txt') self._aliases = PersistentDict(self.aliasfile, 'c') self.sessionhits = {} def load(self): """ load the plugin """ BasePlugin.load(self) self.api('setting.add')('nextnum', 0, int, 'the number of the next alias added', readonly=True) parser = argp.ArgumentParser(add_help=False, description='add an alias') parser.add_argument('original', help='the input to replace', default='', nargs='?') parser.add_argument('replacement', help='the string to replace it with', default='', nargs='?') parser.add_argument('-o', "--overwrite", help="overwrite an alias if it already exists", action="store_true") parser.add_argument('-d', "--disable", help="disable the alias", action="store_true") parser.add_argument('-g', "--group", help="the alias group", default="") self.api('commands.add')('add', self.cmd_add, parser=parser) parser = argp.ArgumentParser(add_help=False, description='remove an alias') parser.add_argument('alias', help='the alias to remove', default='', nargs='?') self.api('commands.add')('remove', self.cmd_remove, parser=parser) parser = argp.ArgumentParser(add_help=False, description='list aliases') parser.add_argument( 'match', help='list only aliases that have this argument in them', default='', nargs='?') self.api('commands.add')('list', self.cmd_list, parser=parser) parser = argp.ArgumentParser(add_help=False, description='toggle enabled flag') parser.add_argument('alias', help='the alias to toggle', default='', nargs='?') self.api('commands.add')('toggle', self.cmd_toggle, parser=parser) parser = argp.ArgumentParser( add_help=False, description='toggle all aliases in a group') parser.add_argument('group', help='the group to toggle', default='', nargs='?') parser.add_argument('-d', "--disable", help="disable the group", action="store_true") self.api('commands.add')('groupt', self.cmd_grouptoggle, parser=parser) parser = argp.ArgumentParser(add_help=False, description='get detail for an alias') parser.add_argument('alias', help='the alias to get details for', default='', nargs='?') self.api('commands.add')('detail', self.cmd_detail, parser=parser) self.api('commands.default')('list') self.api('events.register')('io_execute_event', self.checkalias, prio=2) self.api('events.register')('plugin_%s_savestate' % self.sname, self._savestate) def checkalias(self, args): # pylint: disable=too-many-branches """ this function finds aliases in client input """ data = args['fromdata'].strip() if not data: return args for mem in self._aliases.keys(): if self._aliases[mem]['enabled']: datan = data matchd = re.match(mem, data) if matchd: self.api('send.msg')('matched input on %s' % mem) tlistn = [data] for i in xrange(1, len(matchd.groups()) + 1): tlistn.append(matchd.group(i)) self.api('send.msg')('args: %s' % tlistn) try: datan = self._aliases[mem]['alias'].format(*tlistn) except Exception: # pylint: disable=broad-except self.api('send.traceback')('alias %s had an issue' % (mem)) else: cre = re.compile('^%s' % mem) datan = cre.sub(self._aliases[mem]['alias'], data) if datan != data: if 'trace' in args: args['trace']['changes'].append({'flag':'Modify', 'data':'changed "%s" to "%s"' % \ (data, datan), 'plugin':self.sname}) if not 'hits' in self._aliases[mem]: self._aliases[mem]['hits'] = 0 if not mem in self.sessionhits: self.sessionhits[mem] = 0 self.api('send.msg')('incrementing hits for %s' % mem) self._aliases[mem]['hits'] = self._aliases[mem]['hits'] + 1 self.sessionhits[mem] = self.sessionhits[mem] + 1 self.api('send.msg')('replacing "%s" with "%s"' % \ (data.strip(), datan.strip())) if datan[0:3] == '#bp': self.api('send.execute')(datan, showinhistory=False, fromclient=False) args['fromdata'] = '' args['history'] = False else: args['history'] = False args['fromclient'] = False args['fromdata'] = datan return args def lookup_alias(self, alias): """ lookup an alias by number or name """ nitem = None try: num = int(alias) nitem = None for titem in self._aliases.keys(): if num == self._aliases[titem]['num']: nitem = titem break except ValueError: if alias in self._aliases: nitem = alias return nitem def cmd_add(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Add a alias @CUsage@w: add @Y<originalstring>@w @M<replacementstring>@w @Yoriginalstring@w = The original string to be replaced @Mreplacementstring@w = The new string """ tmsg = [] if args['original'] and args['replacement']: if args['original'] in self._aliases and not args['overwrite']: return True, ['Alias: %s already exists.' % args['original']] else: tmsg.append("@GAdding alias@w : '%s' will be replaced by '%s'" % \ (args['original'], args['replacement'])) self.addalias(args['original'], args['replacement'], args['disable'], args['group']) return True, tmsg else: return False, ['@RPlease include all arguments@w'] def cmd_remove(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Remove a alias @CUsage@w: rem @Y<originalstring>@w @Yoriginalstring@w = The original string """ tmsg = [] if args['alias']: retval = self.removealias(args['alias']) if retval: tmsg.append("@GRemoving alias@w : '%s'" % (retval)) else: tmsg.append("@GCould not remove alias@w : '%s'" % (args['alias'])) return True, tmsg else: return False, ['@RPlease include an alias to remove@w'] def cmd_toggle(self, args): """ toggle the enabled flag """ tmsg = [] if args['alias']: retval = self.togglealias(args['alias']) if retval: if self._aliases[retval]['enabled']: tmsg.append("@GEnabled alias@w : '%s'" % (retval)) else: tmsg.append("@GDisabled alias@w : '%s'" % (retval)) else: tmsg.append("@GDoes not exist@w : '%s'" % (args['alias'])) return True, tmsg else: return False, ['@RPlease include an alias to toggle@w'] def cmd_detail(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Add a alias @CUsage@w: add @Y<originalstring>@w @M<replacementstring>@w @Yoriginalstring@w = The original string to be replaced @Mreplacementstring@w = The new string """ tmsg = [] if args['alias']: alias = self.lookup_alias(args['alias']) if alias: if 'hits' not in self._aliases[alias]: self._aliases[alias]['hits'] = 0 if alias not in self.sessionhits: self.sessionhits[alias] = 0 tmsg.append('%-12s : %d' % ('Num', self._aliases[alias]['num'])) tmsg.append('%-12s : %s' % \ ('Enabled', 'Y' if self._aliases[alias]['enabled'] else 'N')) tmsg.append('%-12s : %d' % ('Total Hits', self._aliases[alias]['hits'])) tmsg.append('%-12s : %d' % ('Session Hits', self.sessionhits[alias])) tmsg.append('%-12s : %s' % ('Alias', alias)) tmsg.append('%-12s : %s' % ('Replacement', self._aliases[alias]['alias'])) tmsg.append('%-12s : %s' % ('Group', self._aliases[alias]['group'])) else: return True, [ '@RAlias does not exits@w : \'%s\'' % (args['alias']) ] return True, tmsg else: return False, ['@RPlease include all arguments@w'] def cmd_list(self, args): """ @G%(name)s@w - @B%(cmdname)s@w List aliases @CUsage@w: list """ tmsg = self.listaliases(args['match']) return True, tmsg def cmd_grouptoggle(self, args): """ toggle all aliases in a group """ tmsg = [] togglea = [] state = not args['disable'] if args['group']: for i in self._aliases: if 'group' not in self._aliases[i]: self._aliases[i]['group'] = '' if self._aliases[i]['group'] == args['group']: self._aliases[i]['enabled'] = state togglea.append('%s' % self._aliases[i]['num']) if togglea: tmsg.append('The following aliases were %s: %s' % \ ('enabled' if state else 'disabled', ','.join(togglea))) else: tmsg.append('No aliases were modified') return True, tmsg else: return False, ['@RPlease include a group to toggle@w'] def addalias(self, item, alias, disabled, group): """ internally add a alias """ num = self.api('setting.gets')('nextnum') self._aliases[item] = { 'alias': alias, 'enabled': not disabled, 'num': num, 'group': group } self._aliases.sync() self.api('setting.change')('nextnum', num + 1) def removealias(self, item): """ internally remove a alias """ alias = self.lookup_alias(item) if alias: del self._aliases[alias] self._aliases.sync() return alias def togglealias(self, item): """ toggle an alias """ alias = self.lookup_alias(item) if alias: self._aliases[alias][ 'enabled'] = not self._aliases[alias]['enabled'] return alias def listaliases(self, match): """ return a table of strings that list aliases """ tmsg = [] for alias in sorted(self._aliases.iteritems(), key=lambda (x, y): y['num']): item = alias[0] if not match or match in item: lalias = self.api('colors.stripansi')( self._aliases[item]['alias']) if len(lalias) > 30: lalias = lalias[:27] + '...' tmsg.append("%4s %2s %-10s %-20s : %s@w" % \ (self._aliases[item]['num'], 'Y' if self._aliases[item]['enabled'] else 'N', self._aliases[item]['group'], item, lalias)) if not tmsg: tmsg = ['None'] else: tmsg.insert( 0, "%4s %2s %-10s %-20s : %s@w" % ('#', 'E', 'Group', 'Alias', 'Replacement')) tmsg.insert(1, '@B' + '-' * 60 + '@w') return tmsg def clearaliases(self): """ clear all aliases """ self._aliases.clear() self._aliases.sync() def reset(self): """ reset the plugin """ BasePlugin.reset(self) self.clearaliases() def _savestate(self, _=None): """ save states """ self._aliases.sync()
class Plugin(BasePlugin): """ a plugin to handle user aliases """ def __init__(self, *args, **kwargs): """ initialize the instance """ BasePlugin.__init__(self, *args, **kwargs) self.aliasfile = os.path.join(self.savedir, 'aliases.txt') self._aliases = PersistentDict(self.aliasfile, 'c') self.sessionhits = {} def load(self): """ load the plugin """ BasePlugin.load(self) self.api.get('setting.add')('nextnum', 0, int, 'the number of the next alias added', readonly=True) parser = argparse.ArgumentParser(add_help=False, description='add an alias') parser.add_argument('original', help='the input to replace', default='', nargs='?') parser.add_argument('replacement', help='the string to replace it with', default='', nargs='?') parser.add_argument('-o', "--overwrite", help="overwrite an alias if it already exists", action="store_true") parser.add_argument('-d', "--disable", help="disable the alias", action="store_true") parser.add_argument('-g', "--group", help="the alias group", default="") self.api.get('commands.add')('add', self.cmd_add, parser=parser) parser = argparse.ArgumentParser(add_help=False, description='remove an alias') parser.add_argument('alias', help='the alias to remove', default='', nargs='?') self.api.get('commands.add')('remove', self.cmd_remove, parser=parser) parser = argparse.ArgumentParser(add_help=False, description='list aliases') parser.add_argument('match', help='list only aliases that have this argument in them', default='', nargs='?') self.api.get('commands.add')('list', self.cmd_list, parser=parser) parser = argparse.ArgumentParser(add_help=False, description='toggle enabled flag') parser.add_argument('alias', help='the alias to toggle', default='', nargs='?') self.api.get('commands.add')('toggle', self.cmd_toggle, parser=parser) parser = argparse.ArgumentParser(add_help=False, description='toggle all aliases in a group') parser.add_argument('group', help='the group to toggle', default='', nargs='?') parser.add_argument('-d', "--disable", help="disable the group", action="store_true") self.api.get('commands.add')('groupt', self.cmd_grouptoggle, parser=parser) parser = argparse.ArgumentParser(add_help=False, description='get detail for an alias') parser.add_argument('alias', help='the alias to get details for', default='', nargs='?') self.api.get('commands.add')('detail', self.cmd_detail, parser=parser) self.api.get('commands.default')('list') self.api.get('events.register')('from_client_event', self.checkalias, prio=2) def checkalias(self, args): """ this function finds aliases in client input """ data = args['fromdata'].strip() if not data: return args for mem in self._aliases.keys(): if self._aliases[mem]['enabled']: datan = data matchd = re.match(mem, data) if matchd: self.api.get('send.msg')('matched input on %s' % mem) tlistn = [data] for i in xrange(1, len(matchd.groups()) + 1): tlistn.append(matchd.group(i)) self.api.get('send.msg')('args: %s' % tlistn) try: datan = self._aliases[mem]['alias'].format(*tlistn) except Exception: # pylint: disable=broad-except self.api.get('send.traceback')('alias %s had an issue' % (mem)) else: cre = re.compile('^%s' % mem) datan = cre.sub(self._aliases[mem]['alias'], data) if datan != data: if not 'hits' in self._aliases[mem]: self._aliases[mem]['hits'] = 0 if not mem in self.sessionhits: self.sessionhits[mem] = 0 self.api.get('send.msg')('incrementing hits for %s' % mem) self._aliases[mem]['hits'] = self._aliases[mem]['hits'] + 1 self.sessionhits[mem] = self.sessionhits[mem] + 1 self.api.get('send.msg')('replacing "%s" with "%s"' % \ (data.strip(), datan.strip())) if datan[0:3] == '#bp': self.api.get('send.execute')(datan, history=False, fromclient=False) args['fromdata'] = '' args['history'] = False else: args['history'] = False args['fromclient'] = False args['fromdata'] = datan return args def lookup_alias(self, alias): """ lookup an alias by number or name """ nitem = None try: num = int(alias) nitem = None for titem in self._aliases.keys(): if num == self._aliases[titem]['num']: nitem = titem break except ValueError: if alias in self._aliases: nitem = alias return nitem def cmd_add(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Add a alias @CUsage@w: add @Y<originalstring>@w @M<replacementstring>@w @Yoriginalstring@w = The original string to be replaced @Mreplacementstring@w = The new string """ tmsg = [] if args['original'] and args['replacement']: if args['original'] in self._aliases and not args['overwrite']: return True, ['Alias: %s already exists.' % args['original']] else: tmsg.append("@GAdding alias@w : '%s' will be replaced by '%s'" % \ (args['original'], args['replacement'])) self.addalias(args['original'], args['replacement'], args['disable'], args['group']) return True, tmsg else: return False, ['@RPlease include all arguments@w'] def cmd_remove(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Remove a alias @CUsage@w: rem @Y<originalstring>@w @Yoriginalstring@w = The original string """ tmsg = [] if args['alias']: retval = self.removealias(args['alias']) if retval: tmsg.append("@GRemoving alias@w : '%s'" % (retval)) else: tmsg.append("@GCould not remove alias@w : '%s'" % (args['alias'])) return True, tmsg else: return False, ['@RPlease include an alias to remove@w'] def cmd_toggle(self, args): """ toggle the enabled flag """ tmsg = [] if args['alias']: retval = self.togglealias(args['alias']) if retval: if self._aliases[retval]['enabled']: tmsg.append("@GEnabled alias@w : '%s'" % (retval)) else: tmsg.append("@GDisabled alias@w : '%s'" % (retval)) else: tmsg.append("@GDoes not exist@w : '%s'" % (args['alias'])) return True, tmsg else: return False, ['@RPlease include an alias to toggle@w'] def cmd_detail(self, args): """ @G%(name)s@w - @B%(cmdname)s@w Add a alias @CUsage@w: add @Y<originalstring>@w @M<replacementstring>@w @Yoriginalstring@w = The original string to be replaced @Mreplacementstring@w = The new string """ tmsg = [] if args['alias']: alias = self.lookup_alias(args['alias']) if alias: if 'hits' not in self._aliases[alias]: self._aliases[alias]['hits'] = 0 if alias not in self.sessionhits: self.sessionhits[alias] = 0 tmsg.append('%-12s : %d' % ('Num', self._aliases[alias]['num'])) tmsg.append('%-12s : %s' % \ ('Enabled', 'Y' if self._aliases[alias]['enabled'] else 'N')) tmsg.append('%-12s : %d' % ('Total Hits', self._aliases[alias]['hits'])) tmsg.append('%-12s : %d' % ('Session Hits', self.sessionhits[alias])) tmsg.append('%-12s : %s' % ('Alias', alias)) tmsg.append('%-12s : %s' % ('Replacement', self._aliases[alias]['alias'])) tmsg.append('%-12s : %s' % ('Group', self._aliases[alias]['group'])) else: return True, ['@RAlias does not exits@w : \'%s\'' % (args['alias'])] return True, tmsg else: return False, ['@RPlease include all arguments@w'] def cmd_list(self, args): """ @G%(name)s@w - @B%(cmdname)s@w List aliases @CUsage@w: list """ tmsg = self.listaliases(args['match']) return True, tmsg def cmd_grouptoggle(self, args): """ toggle all aliases in a group """ tmsg = [] togglea = [] state = not args['disable'] if args['group']: for i in self._aliases: if 'group' not in self._aliases[i]: self._aliases[i]['group'] = '' if self._aliases[i]['group'] == args['group']: self._aliases[i]['enabled'] = state togglea.append('%s' % self._aliases[i]['num']) if togglea: tmsg.append('The following aliases were %s: %s' % \ ('enabled' if state else 'disabled', ','.join(togglea))) else: tmsg.append('No aliases were modified') return True, tmsg else: return False, ['@RPlease include a group to toggle@w'] def addalias(self, item, alias, disabled, group): """ internally add a alias """ num = self.api.get('setting.gets')('nextnum') self._aliases[item] = {'alias':alias, 'enabled':not disabled, 'num':num, 'group':group} self._aliases.sync() self.api.get('setting.change')('nextnum', num + 1) def removealias(self, item): """ internally remove a alias """ alias = self.lookup_alias(item) if alias: del self._aliases[alias] self._aliases.sync() return alias def togglealias(self, item): """ toggle an alias """ alias = self.lookup_alias(item) if alias: self._aliases[alias]['enabled'] = not self._aliases[alias]['enabled'] return alias def listaliases(self, match): """ return a table of strings that list aliases """ tmsg = [] for alias in sorted(self._aliases.iteritems(), key=lambda (x, y): y['num']): item = alias[0] if not match or match in item: lalias = self.api.get('colors.stripansi')(self._aliases[item]['alias']) if len(lalias) > 30: lalias = lalias[:27] + '...' tmsg.append("%4s %2s %-10s %-20s : %s@w" % \ (self._aliases[item]['num'], 'Y' if self._aliases[item]['enabled'] else 'N', self._aliases[item]['group'], item, lalias)) if len(tmsg) == 0: tmsg = ['None'] else: tmsg.insert(0, "%4s %2s %-10s %-20s : %s@w" % ('#', 'E', 'Group', 'Alias', 'Replacement')) tmsg.insert(1, '@B' + '-' * 60 + '@w') return tmsg def clearaliases(self): """ clear all aliases """ self._aliases.clear() self._aliases.sync() def reset(self): """ reset the plugin """ BasePlugin.reset(self) self.clearaliases() def savestate(self): """ save states """ BasePlugin.savestate(self) self._aliases.sync()