diff frontends/src/jp/base.py @ 2155:cee6561ad086

jp (core): added extra_outputs: - extra outputs are output locals to a command which can be used in addition to the generic one which are compatible - added --output_option argument(s) to specify option specific to selected output - Jp.command now references the running command
author Goffi <goffi@goffi.org>
date Thu, 16 Feb 2017 00:49:46 +0100
parents fff88c33442f
children 62dfa6e02f54
line wrap: on
line diff
--- a/frontends/src/jp/base.py	Thu Feb 16 00:44:54 2017 +0100
+++ b/frontends/src/jp/base.py	Thu Feb 16 00:49:46 2017 +0100
@@ -255,8 +255,11 @@
             else:
                 print msg
 
-    def output(self, type_, name, data):
-        self._outputs[type_][name]['callback'](data)
+    def output(self, type_, name, extra_outputs, data):
+        if name in extra_outputs:
+            extra_outputs[name](data)
+        else:
+            self._outputs[type_][name]['callback'](data)
 
     def addOnQuitCallback(self, callback, *args, **kwargs):
         """Add a callback which will be called on quit command
@@ -505,7 +508,7 @@
 
 class CommandBase(object):
 
-    def __init__(self, host, name, use_profile=True, use_output=False,
+    def __init__(self, host, name, use_profile=True, use_output=False, extra_outputs=None,
                        need_connect=None, help=None, **kwargs):
         """Initialise CommandBase
 
@@ -513,6 +516,10 @@
         @param name(unicode): name of the new command
         @param use_profile(bool): if True, add profile selection/connection commands
         @param use_output(bool, unicode): if not False, add --output option
+        @param extra_outputs(dict): list of command specific outputs:
+            key is output name ("default" to use as main output)
+            value is a callable which will format the output (data will be used as only argument)
+            if a key already exists with normal outputs, the extra one will be used
         @param need_connect(bool, None): True if profile connection is needed
             False else (profile session must still be started)
             None to set auto value (i.e. True if use_profile is set)
@@ -546,17 +553,29 @@
 
         # --output option
         if use_output:
+            if extra_outputs is None:
+                extra_outputs = {}
+            self.extra_outputs = extra_outputs
             if use_output == True:
                 use_output = C.OUTPUT_TEXT
             assert use_output in C.OUTPUT_TYPES
             self._output_type = use_output
             output_parent = argparse.ArgumentParser(add_help=False)
-            choices = self.host.getOutputChoices(use_output)
+            choices = set(self.host.getOutputChoices(use_output))
+            choices.update(extra_outputs)
             if not choices:
                 raise exceptions.InternalError("No choice found for {} output type".format(use_output))
-            default = 'default' if 'default' in choices else choices[0]
-            output_parent.add_argument('--output', '-O', choices=choices, default=default, help=_(u"Select output format"))
+            if 'default' in choices:
+                default = 'default'
+            elif 'simple' in choices:
+                default = 'simple'
+            else:
+                default = choices[0]
+            output_parent.add_argument('--output', '-O', choices=sorted(choices), default=default, help=_(u"select output format (default: {})".format(default)))
+            output_parent.add_argument('--output-option', '--oo', type=unicode_decoder, action="append", dest='output_opts', default=[], help=_(u"output specific option"))
             parents.add(output_parent)
+        else:
+            assert extra_outputs is None
 
         # other common options
         use_opts = {k:v for k,v in kwargs.iteritems() if k.startswith('use_')}
@@ -695,7 +714,7 @@
         return self.host.disp(msg, verbosity, error)
 
     def output(self, data):
-        return self.host.output(self._output_type, self.args.output, data)
+        return self.host.output(self._output_type, self.args.output, self.extra_outputs, data)
 
     def add_parser_options(self):
         try:
@@ -714,6 +733,8 @@
         It set stuff like progression callbacks and profile connection
         You should not overide this method: you should call self.start instead
         """
+        # we keep a reference to run command, it may be useful e.g. for outputs
+        self.host.command = self
         # host._need_loop is set here from our current value and not before
         # as the need_loop decision must be taken only by then running command
         self.host._need_loop = self.need_loop