From 77035bfa6837a8e6cd6afbf1e86d077dd108980a Mon Sep 17 00:00:00 2001
From: Marco Mariani <marco.mariani@nexedi.com>
Date: Tue, 23 Apr 2013 08:22:41 +0200
Subject: [PATCH] cli refactoring: console

---
 setup.py              |  1 +
 slapos/cli/config.py  |  9 ++++++
 slapos/cli/console.py | 31 ++++++++++++++++++++
 slapos/client.py      | 66 +++++++++++++++++++++++--------------------
 4 files changed, 77 insertions(+), 30 deletions(-)
 create mode 100644 slapos/cli/console.py

diff --git a/setup.py b/setup.py
index fc879a68c..d2a0cb446 100644
--- a/setup.py
+++ b/setup.py
@@ -77,6 +77,7 @@ setup(name=name,
           'node bang = slapos.cli.bang:BangCommand',
           'node format = slapos.cli.format:FormatCommand',
           'node register = slapos.cli.register:RegisterCommand',
+          'console = slapos.cli.console:ConsoleCommand',
         ]
       },
       test_suite="slapos.tests",
diff --git a/slapos/cli/config.py b/slapos/cli/config.py
index 7e397f402..ff0eb607f 100644
--- a/slapos/cli/config.py
+++ b/slapos/cli/config.py
@@ -10,6 +10,8 @@ class ConfigError(Exception):
     pass
 
 
+
+
 class ConfigCommand(Command):
     "Base class for commands that require a configuration file"
 
@@ -61,3 +63,10 @@ class ConfigCommand(Command):
         self.log.debug('Loading config: %s' % cfg_path)
 
         return self._get_config(cfg_path, required=True)
+
+
+class ClientConfigCommand(ConfigCommand):
+    # XXX does not fallback to SLAPOS_CONFIGURATION
+    default_config_var = 'SLAPOS_CLIENT_CONFIGURATION'
+    default_config_path = '~/.slapos/slapos.cfg'
+
diff --git a/slapos/cli/console.py b/slapos/cli/console.py
new file mode 100644
index 000000000..8fdc2accd
--- /dev/null
+++ b/slapos/cli/console.py
@@ -0,0 +1,31 @@
+# -*- coding: utf-8 -*-
+
+import logging
+
+from slapos.cli.config import ClientConfigCommand
+from slapos.client import init, do_console, ClientConfig
+
+
+class ConsoleCommand(ClientConfigCommand):
+    """
+    slapconsole allows you interact with slap API. You can play with the global
+    "slap" object and with the global "request" method.
+
+    examples :
+    >>> # Request instance
+    >>> request(kvm, "myuniquekvm")
+    >>> # Request software installation on owned computer
+    >>> supply(kvm, "mycomputer")
+    >>> # Fetch instance informations on already launched instance
+    >>> request(kvm, "myuniquekvm").getConnectionParameter("url")
+    """
+    # XXX TODO: docstring is printed without newlines
+
+    log = logging.getLogger(__name__)
+
+    def take_action(self, args):
+        configuration_parser = self.fetch_config(args)
+        config = ClientConfig(args, configuration_parser)
+        local = init(config)
+        do_console(local)
+
diff --git a/slapos/client.py b/slapos/client.py
index 86bc55f84..95d146719 100644
--- a/slapos/client.py
+++ b/slapos/client.py
@@ -115,8 +115,18 @@ def check_request_args():
   return args
 
 
-class Config:
-  def __init__(self, option_dict, configuration_file_path=None):
+def get_config_parser(path):
+  configuration_parser = ConfigParser.SafeConfigParser()
+  path = os.path.expanduser(path)
+  if not os.path.isfile(path):
+    raise OSError('Specified configuration file %s does not exist. Exiting.' % path)
+  configuration_parser.read(path)
+  return configuration_parser
+
+
+
+class ClientConfig(object):
+  def __init__(self, option_dict, configuration_parser=None):
     """
     Set options given by parameters.
     """
@@ -124,14 +134,6 @@ class Config:
     for option, value in option_dict.__dict__.items():
       setattr(self, option, value)
 
-    # Load configuration file
-    configuration_parser = ConfigParser.SafeConfigParser()
-    if configuration_file_path:
-      configuration_file_path = os.path.expanduser(configuration_file_path)
-      if not os.path.isfile(configuration_file_path):
-        raise OSError('Specified configuration file %s does not exist.'
-            ' Exiting.' % configuration_file_path)
-      configuration_parser.read(configuration_file_path)
     # Merges the arguments and configuration
     try:
       configuration_dict = dict(configuration_parser.items('slapconsole'))
@@ -194,7 +196,7 @@ def request():
   # Parse arguments and inititate needed parameters
   # XXX-Cedric: move argument parsing to main entry point
   options = check_request_args()
-  config = Config(options, options.configuration_file)
+  config = ClientConfig(options, get_config_parser(options.configuration_file))
   local = init(config)
   # Request instance
   print("Requesting %s..." % config.reference)
@@ -257,7 +259,7 @@ def supply():
                       help="Target node")
   args = parser.parse_args()
 
-  config = Config(args, args.configuration_file)
+  config = ClientConfig(args, get_config_parser(args.configuration_file))
   _supply(args.software_url, args.node, init(config))
 
 def remove():
@@ -274,27 +276,11 @@ def remove():
                       help="Target node")
   args = parser.parse_args()
 
-  config = Config(args, args.configuration_file)
+  config = ClientConfig(args, get_config_parser(args.configuration_file))
   _supply(args.software_url, args.node, init(config), remove=True)
 
 
-def slapconsole():
-  """Ran when invoking slapconsole"""
-  # Parse arguments
-  usage = """usage: %s [options] CONFIGURATION_FILE
-slapconsole allows you interact with slap API. You can play with the global
-"slap" object and with the global "request" method.
-
-examples :
-  >>> # Request instance
-  >>> request(kvm, "myuniquekvm")
-  >>> # Request software installation on owned computer
-  >>> supply(kvm, "mycomputer")
-  >>> # Fetch instance informations on already launched instance
-  >>> request(kvm, "myuniquekvm").getConnectionParameter("url")""" % sys.argv[0]
-  config = Config(*Parser(usage=usage).check_args())
-  local = init(config)
-
+def do_console(local):
   # try to enable readline with completion and history
   try:
     import readline
@@ -317,3 +303,23 @@ examples :
 
   __import__("code").interact(banner="", local=local)
 
+
+def slapconsole():
+  """Ran when invoking slapconsole"""
+  # Parse arguments
+  usage = """usage: %s [options] CONFIGURATION_FILE
+slapconsole allows you interact with slap API. You can play with the global
+"slap" object and with the global "request" method.
+
+examples :
+  >>> # Request instance
+  >>> request(kvm, "myuniquekvm")
+  >>> # Request software installation on owned computer
+  >>> supply(kvm, "mycomputer")
+  >>> # Fetch instance informations on already launched instance
+  >>> request(kvm, "myuniquekvm").getConnectionParameter("url")""" % sys.argv[0]
+  options, configuration_file_path = Parser(usage=usage).check_args()
+  config = ClientConfig(options, get_config_parser(configuration_file_path))
+  local = init(config)
+  do_console(local)
+
-- 
2.30.9