You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by ro...@apache.org on 2018/04/10 22:41:51 UTC

[cloudstack-cloudmonkey] 01/02: cloudmonkey: purge legacy files

This is an automated email from the ASF dual-hosted git repository.

rohit pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/cloudstack-cloudmonkey.git

commit 7b55fb417ac6788b009c1caf040f2a9dbb6e0031
Author: Rohit Yadav <ro...@apache.org>
AuthorDate: Wed Apr 11 04:02:40 2018 +0530

    cloudmonkey: purge legacy files
    
    Signed-off-by: Rohit Yadav <ro...@apache.org>
---
 .gitignore                  |  28 --
 Dockerfile                  |  36 --
 Makefile                    |  41 --
 cloudmonkey/__init__.py     |  23 --
 cloudmonkey/cachemaker.py   | 182 ---------
 cloudmonkey/cloudmonkey.py  | 937 --------------------------------------------
 cloudmonkey/config.py       | 209 ----------
 cloudmonkey/precache.py     |  19 -
 cloudmonkey/printer.py      | 124 ------
 cloudmonkey/requester.py    | 335 ----------------
 config.docker               |  25 --
 docs/.gitignore             |   1 -
 docs/Makefile               | 177 ---------
 docs/source/cloudmonkey.rst |  62 ---
 docs/source/conf.py         | 262 -------------
 docs/source/index.rst       |  37 --
 docs/source/modules.rst     |   7 -
 setup.cfg                   |   7 -
 setup.py                    |  86 ----
 19 files changed, 2598 deletions(-)

diff --git a/.gitignore b/.gitignore
deleted file mode 100644
index 63c8cd1..0000000
--- a/.gitignore
+++ /dev/null
@@ -1,28 +0,0 @@
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-
-dist/
-*~
-*.log
-*.pyc
-*.egginfo/
-*.egg-info/
-.DS_Store
-*.swp
-build/
-.*
-!.gitignore
diff --git a/Dockerfile b/Dockerfile
deleted file mode 100644
index 696974d..0000000
--- a/Dockerfile
+++ /dev/null
@@ -1,36 +0,0 @@
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-# 
-#   http://www.apache.org/licenses/LICENSE-2.0
-# 
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-#
-#
-FROM python:2
-
-MAINTAINER "Apache CloudStack" <de...@cloudstack.apache.org>
-LABEL Description="Apache CloudStack CloudMonkey; Python based CloudStack command line interface"
-LABEL Vendor="Apache.org"
-LABEL License=ApacheV2
-LABEL Version=5.3.3
-
-COPY . /cloudstack-cloudmonkey
-RUN pip install requests
-RUN (cd /cloudstack-cloudmonkey; python setup.py build)
-RUN (cd /cloudstack-cloudmonkey; python setup.py install)
-
-RUN mkdir -p /cloudmonkey
-WORKDIR /cloudmonkey
-COPY config.docker /cloudmonkey/config
-
-ENTRYPOINT ["cloudmonkey", "-c", "/cloudmonkey/config"]
\ No newline at end of file
diff --git a/Makefile b/Makefile
deleted file mode 100644
index 182cbce..0000000
--- a/Makefile
+++ /dev/null
@@ -1,41 +0,0 @@
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-
-all: clean buildwithcache
-
-runtests:
-	nosetests -v --verbosity=3
-
-buildwithcache: buildcache build
-
-build:
-	python setup.py build
-	python setup.py sdist
-
-check:
-	pep8 cloudmonkey/*.py
-
-buildcache:
-	python cloudmonkey/cachemaker.py
-	mv -f precache.py cloudmonkey/
-
-install: clean
-	python setup.py sdist
-	pip install --upgrade dist/cloudmonkey-*.tar.gz
-
-clean:
-	rm -frv build dist *egg-info
diff --git a/cloudmonkey/__init__.py b/cloudmonkey/__init__.py
deleted file mode 100644
index cf689e7..0000000
--- a/cloudmonkey/__init__.py
+++ /dev/null
@@ -1,23 +0,0 @@
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-
-try:
-    from config import __version__, __description__
-    from config import __maintainer__, __maintaineremail__
-    from config import __project__, __projecturl__, __projectemail__
-except ImportError, e:
-    print e
diff --git a/cloudmonkey/cachemaker.py b/cloudmonkey/cachemaker.py
deleted file mode 100644
index 2f2fa87..0000000
--- a/cloudmonkey/cachemaker.py
+++ /dev/null
@@ -1,182 +0,0 @@
-# -*- coding: utf-8 -*-
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-
-try:
-    import json
-    import os
-    import types
-
-    from config import config_fields
-except ImportError, e:
-    import sys
-    print "ImportError", e
-    sys.exit(1)
-
-
-def getvalue(dictionary, key):
-    if key in dictionary:
-        return dictionary[key]
-    else:
-        return None
-
-
-def splitcsvstring(string):
-    if string is not None:
-        return filter(lambda x: x.strip() != '', string.split(','))
-    else:
-        return []
-
-
-def splitverbsubject(string):
-    idx = 0
-    for char in string:
-        if char.islower():
-            idx += 1
-        else:
-            break
-    return string[:idx].lower(), string[idx:].lower()
-
-
-def savecache(apicache, json_file):
-    """
-    Saves apicache dictionary as json_file, returns dictionary as indented str
-    """
-    if apicache is None or apicache is {}:
-        return ""
-    apicachestr = json.dumps(apicache, indent=2)
-    with open(json_file, 'w') as cache_file:
-        cache_file.write(apicachestr)
-    return apicachestr
-
-
-def loadcache(json_file):
-    """
-    Loads json file as dictionary, feeds it to monkeycache and spits result
-    """
-    f = open(json_file, 'r')
-    data = f.read()
-    f.close()
-    try:
-        apicache = json.loads(data)
-    except ValueError, e:
-        print "Error processing json:", json_file, e
-        return {}
-    return apicache
-
-
-def monkeycache(apis):
-    """
-    Feed this a dictionary of api bananas, it spits out processed cache
-    """
-    if isinstance(type(apis), types.NoneType) or apis is None:
-        return {}
-
-    responsekey = filter(lambda x: 'response' in x, apis.keys())
-
-    if len(responsekey) == 0:
-        print "[monkeycache] Invalid dictionary, has no response"
-        return None
-    if len(responsekey) != 1:
-        print "[monkeycache] Multiple responsekeys, chosing first one"
-
-    responsekey = responsekey[0]
-    verbs = set()
-    cache = {}
-    cache['count'] = getvalue(apis[responsekey], 'count')
-    cache['asyncapis'] = []
-
-    apilist = getvalue(apis[responsekey], 'api')
-    if apilist is None:
-        print "[monkeycache] Server response issue, no apis found"
-
-    for api in apilist:
-        name = getvalue(api, 'name')
-        verb, subject = splitverbsubject(name)
-
-        apidict = {}
-        apidict['name'] = name
-        apidict['description'] = getvalue(api, 'description')
-        apidict['isasync'] = getvalue(api, 'isasync')
-        if apidict['isasync']:
-            cache['asyncapis'].append(name)
-        apidict['related'] = splitcsvstring(getvalue(api, 'related'))
-
-        required = []
-        apiparams = []
-        for param in getvalue(api, 'params'):
-            apiparam = {}
-            apiparam['name'] = getvalue(param, 'name')
-            apiparam['description'] = getvalue(param, 'description')
-            apiparam['required'] = (getvalue(param, 'required') is True)
-            apiparam['length'] = int(getvalue(param, 'length'))
-            apiparam['type'] = getvalue(param, 'type')
-            apiparam['related'] = splitcsvstring(getvalue(param, 'related'))
-            if apiparam['required']:
-                required.append(apiparam['name'])
-            apiparams.append(apiparam)
-
-        apidict['requiredparams'] = required
-        apidict['params'] = apiparams
-        apidict['response'] = getvalue(api, 'response')
-        if verb not in cache:
-            cache[verb] = {}
-        cache[verb][subject] = apidict
-        verbs.add(verb)
-
-    cache['verbs'] = list(verbs)
-    return cache
-
-
-def main(json_file):
-    """
-    cachemaker.py creates a precache datastore of all available apis of
-    CloudStack and dumps the precache dictionary in an
-    importable python module. This way we cheat on the runtime overhead of
-    completing commands and help docs. This reduces the overall search and
-    cache_miss (computation) complexity from O(n) to O(1) for any valid cmd.
-    """
-    f = open("precache.py", "w")
-    f.write("""# -*- coding: utf-8 -*-
-# Auto-generated code by cachemaker.py
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.""")
-    f.write("\napicache = %s" % loadcache(json_file))
-    f.close()
-
-if __name__ == "__main__":
-    cache_file = config_fields['core']['cache_file']
-    print "[cachemaker] Pre-caching using user's cloudmonkey cache", cache_file
-    if os.path.exists(cache_file):
-        main(cache_file)
-    else:
-        print "[cachemaker] Unable to cache apis, file not found", cache_file
-        print "[cachemaker] Run cloudmonkey sync to generate cache"
diff --git a/cloudmonkey/cloudmonkey.py b/cloudmonkey/cloudmonkey.py
deleted file mode 100644
index b106362..0000000
--- a/cloudmonkey/cloudmonkey.py
+++ /dev/null
@@ -1,937 +0,0 @@
-#!/usr/bin/python
-# -*- coding: utf-8 -*-
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-
-try:
-    import argcomplete
-    import argparse
-    import atexit
-    import cmd
-    import csv
-    import copy
-    import json
-    import logging
-    import os
-    import shlex
-    import sys
-    import time
-    import types
-
-    from cachemaker import loadcache, savecache, monkeycache, splitverbsubject
-    from config import __version__, __description__, __projecturl__
-    from config import display_types
-    from config import read_config, write_config, config_file, default_profile
-    from dicttoxml import dicttoxml
-    from optparse import OptionParser
-    from prettytable import PrettyTable
-    from printer import monkeyprint
-    from requester import monkeyrequest
-    from requester import login
-    from requester import logout
-    from urlparse import urlparse
-    from xml.dom.minidom import parseString
-except ImportError, e:
-    print("Import error in %s : %s" % (__name__, e))
-    import sys
-    sys.exit()
-
-try:
-    from precache import apicache
-except ImportError:
-    apicache = {'count': 0, 'verbs': [], 'asyncapis': []}
-
-normal_readline = True
-# Fix terminal env before importing readline
-# Without it, char ESC[?1034h gets printed in output
-# There is not TERM variable in some environment such as Docker.
-if 'TERM' not in os.environ or os.environ['TERM'].startswith('xterm'):
-    os.environ['TERM'] = 'vt100'
-try:
-    import readline
-except ImportError, e:
-    print("Module readline not found, autocompletions will fail", e)
-else:
-    import rlcompleter
-    readline_doc = getattr(readline, '__doc__', '')
-    if readline_doc is not None and 'libedit' in readline_doc:
-        readline.parse_and_bind("bind ^I rl_complete")
-        readline.parse_and_bind("bind ^R em-inc-search-prev")
-        normal_readline = False
-    else:
-        readline.parse_and_bind("tab: complete")
-
-log_fmt = '%(asctime)s - %(filename)s:%(lineno)s - [%(levelname)s] %(message)s'
-logger = logging.getLogger(__name__)
-
-
-class CloudMonkeyShell(cmd.Cmd, object):
-    intro = ("☁ Apache CloudStack 🐵 cloudmonkey " + __version__ +
-             ". Type help or ? to list commands.\n")
-    ruler = "="
-    config_options = []
-    profile_names = []
-    verbs = []
-    interpreterMode = False
-    error_on_last_command = False
-    param_cache = {}
-    prompt = "🐵 > "
-    protocol = "http"
-    host = "localhost"
-    port = "8080"
-    path = "/client/api"
-    hook_count = 0
-
-    def __init__(self, pname, cfile):
-        self.default_apis = self.completenames('')
-        self.program_name = pname
-        self.config_file = cfile
-        self.config_options = read_config(self.get_attr, self.set_attr,
-                                          self.config_file)
-        self.loadcache()
-        self.init_credential_store()
-        logging.basicConfig(filename=self.log_file,
-                            level=logging.DEBUG, format=log_fmt)
-        logger.debug("Loaded config fields:\n%s" % map(lambda x: "%s=%s" %
-                                                       (x, getattr(self, x)),
-                                                       self.config_options))
-        cmd.Cmd.__init__(self)
-
-        try:
-            if os.path.exists(self.history_file):
-                readline.read_history_file(self.history_file)
-        except IOError, e:
-            logger.debug(u"Error: Unable to read history. " + unicode(e))
-        atexit.register(readline.write_history_file, self.history_file)
-
-    def init_credential_store(self):
-        self.credentials = {'apikey': self.apikey, 'secretkey': self.secretkey,
-                            'domain': self.domain, 'username': self.username,
-                            'password': self.password,
-                            'signatureversion': self.signatureversion}
-        parsed_url = urlparse(self.url)
-        self.protocol = "http" if not parsed_url.scheme else parsed_url.scheme
-        self.host = parsed_url.netloc
-        self.port = "8080" if not parsed_url.port else parsed_url.port
-        self.path = parsed_url.path
-        self.set_prompt()
-
-    def get_prompt(self):
-        return self.prompt.split(") ")[-1]
-
-    def set_prompt(self):
-        self.prompt = "(%s) %s" % (self.profile, self.get_prompt())
-
-    def get_attr(self, field):
-        return getattr(self, field)
-
-    def set_attr(self, field, value):
-        return setattr(self, field, value)
-
-    def emptyline(self):
-        pass
-
-    def cmdloop(self, intro=None):
-        self.interpreterMode = True
-        print(self.intro)
-        print "Using management server profile:", self.profile, "\n"
-        while True:
-            try:
-                super(CloudMonkeyShell, self).cmdloop(intro="")
-            except KeyboardInterrupt:
-                print("^C")
-
-    def precmd(self, line):
-        self.hook_count -= 1
-        if self.hook_count <= 0:
-            self.hook_count = 0
-            readline.set_startup_hook()
-        return line
-
-    def loadcache(self):
-        if os.path.exists(self.cache_file):
-            self.apicache = loadcache(self.cache_file)
-        else:
-            self.apicache = apicache
-        if 'verbs' in self.apicache:
-            self.verbs = self.apicache['verbs']
-
-        for verb in self.verbs:
-            handler_name = "do_" + str(verb)
-            handler_doc = str("%ss resources" % verb.capitalize())
-
-            if hasattr(self, handler_name) and getattr(self, handler_name).__doc__ == handler_doc:
-                continue
-
-            def add_grammar(verb):
-                default_handler = None
-                if self.default_apis.__contains__(verb):
-                    default_handler = getattr(self, handler_name)
-
-                def grammar_closure(self, args):
-                    if not args:
-                        if default_handler:
-                            default_handler(args)
-                        return
-                    args = args.decode("utf-8")
-                    if self.pipe_runner(u"{0} {1}".format(verb, args)):
-                        return
-                    if ' --help' in args or ' -h' in args:
-                        self.do_help("%s %s" % (verb, args))
-                        return
-                    try:
-                        args_partition = args.partition(" ")
-                        cmd = self.apicache[verb][args_partition[0]]['name']
-                        args = args_partition[2]
-                    except KeyError, e:
-                        if default_handler:
-                            default_handler(args)
-                        else:
-                            self.monkeyprint("Error: invalid %s api arg " % verb,
-                                         str(e))
-                        return
-                    self.default(u"{0} {1}".format(cmd, args))
-                return grammar_closure
-
-            grammar_handler = add_grammar(verb)
-            grammar_handler.__doc__ = handler_doc
-            grammar_handler.__name__ = handler_name
-            setattr(self.__class__, grammar_handler.__name__, grammar_handler)
-
-    def monkeyprint(self, *args):
-        output = u""
-        try:
-            for arg in args:
-                if isinstance(type(arg), types.NoneType) or not arg:
-                    continue
-                if not (isinstance(arg, str) or isinstance(arg, unicode)):
-                    arg = unicode(arg)
-                output += arg
-        except Exception, e:
-            print(str(e))
-
-        output = output.encode("utf-8")
-        if self.color == 'true':
-            monkeyprint(output)
-        else:
-            if output.startswith("Error"):
-                sys.stderr.write(output + "\n")
-                sys.stderr.flush()
-            else:
-                print output
-
-    def print_result(self, result, result_filter=[]):
-        if not result or len(result) == 0:
-            return
-
-        filtered_result = copy.deepcopy(result)
-        if result_filter and isinstance(result_filter, list) \
-                and len(result_filter) > 0:
-            tfilter = {}  # temp var to hold a dict of the filters
-            tresult = filtered_result  # dupe the result to filter
-            if result_filter:
-                for res in result_filter:
-                    tfilter[res] = 1
-                for okey, oval in result.iteritems():
-                    if isinstance(oval, dict):
-                        for tkey in oval:
-                            if tkey not in tfilter:
-                                try:
-                                    del(tresult[okey][oval][tkey])
-                                except:
-                                    pass
-                    elif isinstance(oval, list):
-                        for x in range(len(oval)):
-                            if isinstance(oval[x], dict):
-                                for tkey in oval[x]:
-                                    if tkey not in tfilter:
-                                        try:
-                                            del(tresult[okey][x][tkey])
-                                        except:
-                                            pass
-                            else:
-                                try:
-                                    del(tresult[okey][x])
-                                except:
-                                    pass
-            filtered_result = tresult
-
-        def print_result_json(result):
-            self.monkeyprint(json.dumps(result,
-                                        sort_keys=True,
-                                        indent=2,
-                                        ensure_ascii=False,
-                                        separators=(',', ': ')))
-
-        def print_result_xml(result):
-            custom_root = "CloudStack-%s" % self.profile.replace(" ", "_")
-            xml = dicttoxml(result, attr_type=False, custom_root=custom_root)
-            self.monkeyprint(parseString(xml).toprettyxml())
-
-        def print_result_csv(result):
-            if "count" in result:
-                result.pop("count")
-
-            if len(result.keys()) == 1:
-                item = result[result.keys()[0]]
-                if isinstance(item, list):
-                    result = item
-                elif isinstance(item, dict):
-                    result = [item]
-
-            if isinstance(result, list) and len(result) > 0:
-                if isinstance(result[0], dict):
-                    keys = result[0].keys()
-                    writer = csv.DictWriter(sys.stdout, keys)
-                    print ','.join(keys)
-                    for item in result:
-                        row = {}
-                        for k in keys:
-                            if k not in item:
-                                row[k] = None
-                            else:
-                                if type(item[k]) is unicode:
-                                    row[k] = item[k].encode('utf8')
-                                else:
-                                    row[k] = item[k]
-                        writer.writerow(row)
-            elif isinstance(result, dict):
-                keys = result.keys()
-                writer = csv.DictWriter(sys.stdout, keys)
-                print ','.join(keys)
-                writer.writerow(result)
-
-        def print_result_tabular(result):
-            def print_table(printer, toprow):
-                if printer:
-                    self.monkeyprint(printer.get_string())
-                return PrettyTable(toprow)
-            printer = None
-            toprow = []
-            if not result:
-                return
-            toprow = set(reduce(lambda x, y: x + y, map(lambda x: x.keys(),
-                         filter(lambda x: isinstance(x, dict), result))))
-            printer = print_table(printer, toprow)
-            for node in result:
-                if not node:
-                    continue
-                for key in toprow:
-                    if key not in node:
-                        node[key] = ''
-                row = map(lambda x: node[x], toprow)
-                if printer and row:
-                    printer.add_row(row)
-            print_table(printer, toprow)
-
-        def print_result_as_dict(result):
-            for key in sorted(result.keys(), key=lambda x:
-                              x not in ['id', 'count', 'name'] and x):
-                if isinstance(result[key], list):
-                    self.monkeyprint(key + ":")
-                    print_result_as_list(result[key])
-                elif isinstance(result[key], dict):
-                    self.monkeyprint(key + ":")
-                    print_result_as_dict(result[key])
-                else:
-                    value = unicode(result[key])
-                    self.monkeyprint(key, " = ", value)
-
-        def print_result_as_list(result):
-            for idx, node in enumerate(result):
-                if isinstance(node, dict):
-                    if self.display == 'table':
-                        print_result_tabular(result)
-                        break
-                    print_result_as_dict(node)
-                elif isinstance(node, list):
-                    print_result_as_list(node)
-                else:
-                    self.monkeyprint(filtered_result)
-                if result and node and (idx+1) < len(result):
-                    self.monkeyprint(self.ruler * 80)
-
-        if self.display == "json":
-            print_result_json(filtered_result)
-            return
-
-        if self.display == "xml":
-            print_result_xml(filtered_result)
-            return
-
-        if self.display == "csv":
-            print_result_csv(filtered_result)
-            return
-
-        if isinstance(filtered_result, dict):
-            print_result_as_dict(filtered_result)
-        elif isinstance(filtered_result, list):
-            print_result_as_list(filtered_result)
-        else:
-            self.monkeyprint(filtered_result)
-
-    def make_request(self, command, args={}, isasync=False):
-        self.error_on_last_command = False
-        response, error = monkeyrequest(command, args, isasync,
-                                        self.asyncblock, logger,
-                                        self.url, self.credentials,
-                                        self.timeout, self.expires,
-                                        self.verifysslcert == 'true',
-                                        self.signatureversion)
-        if error:
-            self.monkeyprint(u"Error {0}".format(error))
-            self.error_on_last_command = True
-        return response
-
-    def update_param_cache(self, api, result={}):
-        if not api:
-            return
-        logger.debug("Updating param cache for %s API" % api)
-        responsekey = filter(lambda x: 'response' in x, result.keys())[0]
-        result = result[responsekey]
-        options = []
-        uuids = []
-        for key in result.keys():
-            if isinstance(result[key], list):
-                for element in result[key]:
-                    if 'id' in element.keys():
-                        uuid = unicode(element['id'])
-                        name = ""
-                        keyspace = ["name", "displayname",
-                                    "username", "description"]
-                        for name_key in keyspace:
-                            if name_key in element.keys():
-                                name = element[name_key]
-                                break
-                        options.append((uuid, name,))
-                        uuids.append(uuid)
-        self.param_cache[api] = {}
-        self.param_cache[api]["ts"] = int(time.time())
-        self.param_cache[api]["options"] = sorted(options)
-        return sorted(uuids)
-
-    def default(self, args):
-        try:
-            args = args.strip()
-            args.decode("utf-8")
-        except UnicodeError, ignore:
-            args = args.encode("utf-8")
-
-        if self.pipe_runner(args):
-            return
-
-        apiname = args.partition(' ')[0]
-        verb, subject = splitverbsubject(apiname)
-
-        lexp = shlex.shlex(args)
-        lexp.whitespace = " "
-        lexp.whitespace_split = True
-        lexp.posix = True
-        args = []
-        while True:
-            try:
-                next_val = lexp.next()
-                if not next_val:
-                    break
-                next_val = next_val.decode("utf-8")
-                args.append(next_val.replace(u'\x00', u''))
-            except ValueError, err:
-                self.monkeyprint("Command parsing error: ", err)
-                return
-
-        args_dict = dict(map(lambda x: [x.partition("=")[0],
-                                        x.partition("=")[2]],
-                             args[1:])[x] for x in range(len(args) - 1))
-
-        field_filter = []
-        if 'filter' in args_dict:
-            field_filter = filter(lambda x: x.strip() != '',
-                                  args_dict.pop('filter').split(','))
-            field_filter = list(set(field_filter))
-
-        missing = []
-        if verb in self.apicache and subject in self.apicache[verb]:
-            missing = filter(lambda x: x not in [key.split('[')[0].lower()
-                                                 for key in args_dict],
-                             self.apicache[verb][subject]['requiredparams'])
-
-        if len(missing) > 0:
-            self.monkeyprint("Missing arguments: ", ' '.join(missing))
-            return
-
-        isasync = False
-        if 'asyncapis' in self.apicache:
-            if apiname.decode("utf-8") in self.apicache["asyncapis"]:
-                isasync = True
-
-        result = self.make_request(apiname, args_dict, isasync)
-
-        if not result or not isinstance(result, dict):
-            if isinstance(result, unicode):
-                result = result.decode("utf-8")
-            logger.debug("Invalid command result: %s" % result)
-            return
-
-        try:
-            responsekeys = filter(lambda x: 'response' in x, result.keys())
-            for responsekey in responsekeys:
-                self.print_result(result[responsekey], field_filter)
-            if apiname.startswith("list") and "id" not in args_dict:
-                self.update_param_cache(apiname, result)
-        except Exception as e:
-            self.monkeyprint("Error on parsing and printing ", e)
-
-    def completedefault(self, text, line, begidx, endidx):
-        partitions = line[:endidx].partition(" ")
-        verb = partitions[0].strip()
-        rline = partitions[2].lstrip().partition(" ")
-        subject = rline[0]
-        separator = rline[1]
-        params = rline[2].lstrip()
-
-        if verb not in self.verbs:
-            return []
-
-        autocompletions = []
-        search_string = ""
-
-        if separator != " ":   # Complete verb subjects
-            autocompletions = map(lambda x: x + " ",
-                                  self.apicache[verb].keys())
-            search_string = subject
-        else:                  # Complete subject params
-            autocompletions = map(lambda x: x + "=",
-                                  map(lambda x: x['name'],
-                                      self.apicache[verb][subject]['params']))
-            search_string = text
-            if self.paramcompletion == 'true':
-                param = line[:endidx].split(" ")[-1]
-                idx = param.find("=")
-                value = param[idx + 1:]
-                param = param[:idx]
-                if param == "filter":
-                    response_params = self.apicache[verb][subject]["response"]
-                    used = filter(lambda x: x.strip() != "",
-                                  value.split(",")[:-1])
-                    unused = map(lambda x: x['name'] + ",", filter(lambda x:
-                                 "name" in x and x["name"] not in used,
-                                 response_params))
-                    last_value = value.split(",")[-1]
-                    if last_value:
-                        unused = filter(lambda x: x.startswith(last_value),
-                                        unused)
-                    suffix = ",".join(used)
-                    if suffix:
-                        suffix += ","
-                    global normal_readline
-                    if normal_readline:
-                        return filter(lambda x: x.startswith(last_value),
-                                      map(lambda x: x, unused))
-                    else:  # OSX fix
-                        return filter(lambda x: x.startswith(value),
-                                      map(lambda x: suffix + x, unused))
-                elif len(value) < 36 and idx != -1:
-                    api = None
-                    logger.debug("[Paramcompl] For %s %s %s=" % (verb, subject,
-                                                                 param))
-                    if "id" in param:
-                        logger.debug("[Paramcompl] Using 'list' heuristics")
-                        if param == "id" or param == "ids":
-                            entity = subject
-                        else:
-                            entity = param.replace("id", "")
-                        apis = []
-                        for resource in self.apicache["list"]:
-                            if resource.startswith(entity):
-                                api = self.apicache["list"][resource]['name']
-                                if (entity + "s") == resource.lower():
-                                    break
-                                apis.append(api)
-                                api = None
-                        if len(apis) > 0 and not api:
-                            logger.debug("[Paramcompl] APIs: %s" % apis)
-                            api = min(apis, key=len)
-                        logger.debug("[Paramcompl] Possible API: %s" % api)
-                    if not api:
-                        logger.debug("[Paramcompl] Using relative approx")
-                        params = self.apicache[verb][subject]['params']
-                        arg = filter(lambda x: x['name'] == param, params)[0]
-                        if "type" in arg and arg["type"] == "boolean":
-                            return filter(lambda x: x.startswith(value),
-                                          ["true ", "false "])
-                        related = arg['related']
-                        apis = filter(lambda x: 'list' in x, related)
-                        logger.debug("[Paramcompl] Related APIs: %s" % apis)
-                        if len(apis) > 0:
-                            api = apis[0]
-                        else:
-                            if param == "account":
-                                api = "listAccounts"
-                            else:
-                                return
-                    uuids = []
-                    cache_burst_ts = int(time.time()) - 900
-                    logger.debug("Trying paramcompletion using API: %s" % api)
-                    if api in self.param_cache.keys() and \
-                        len(self.param_cache[api]["options"]) > 0 and \
-                            self.param_cache[api]["ts"] > cache_burst_ts:
-                        for option in self.param_cache[api]["options"]:
-                            uuid = option[0]
-                            if uuid.startswith(value):
-                                uuids.append(uuid)
-                    else:
-                        api_args = {'listall': 'true', 'templatefilter': 'all'}
-                        response = self.make_request(api, args=api_args)
-                        if not response:
-                            return
-                        uuids = self.update_param_cache(api, response)
-                    if len(uuids) > 1:
-                        print
-                        options = sorted(self.param_cache[api]["options"],
-                                         key=lambda x: x[1])
-                        for option in options:
-                            uuid = option[0]
-                            name = option[1]
-                            if uuid.startswith(value):
-                                print uuid, name
-                    autocompletions = map(lambda x: x + " ", uuids)
-                    search_string = value
-
-        if subject != "" and line.split(" ")[-1].find('=') == -1:
-            autocompletions.append("filter=")
-        return [s for s in autocompletions if s.startswith(search_string)]
-
-    def do_sync(self, args):
-        """
-        Asks cloudmonkey to discovery and sync apis available on user specified
-        CloudStack host server which has the API discovery plugin, on failure
-        it rollbacks last datastore or api precached datastore.
-        """
-        response = self.make_request("listApis")
-        if not response:
-            monkeyprint("Failed to sync apis, please check your config?")
-            monkeyprint("Note: `sync` requires api discovery service enabled" +
-                        " on the CloudStack management server")
-            return
-        self.apicache = monkeycache(response)
-        savecache(self.apicache, self.cache_file)
-        monkeyprint("%s APIs discovered and cached" % self.apicache["count"])
-        self.loadcache()
-
-    def do_api(self, args):
-        """
-        Make raw api calls. Syntax: api <apiName> <args>=<values>.
-
-        Example:
-        api listAccount listall=true
-        """
-        if len(args) > 0:
-            return self.default(args)
-        else:
-            self.monkeyprint("Please use a valid syntax")
-
-    def do_set(self, args):
-        """
-        Set config for cloudmonkey. For example, options can be:
-        url, auth, log_file, history_file
-        You may also edit your ~/.cloudmonkey_config instead of using set.
-
-        Example:
-        set url http://localhost:8080/client/api
-        set prompt 🐵 cloudmonkey>
-        set log_file /var/log/cloudmonkey.log
-        """
-        args = args.strip().partition(" ")
-        key, value = (args[0].strip(), args[2].strip())
-        if not key:
-            return
-        allowed_blank_keys = ["username", "password", "apikey", "secretkey",
-                              "domain"]
-        if key not in allowed_blank_keys and not value:
-            print "Blank value of %s is not allowed" % key
-            return
-
-        self.prompt = self.get_prompt()
-        setattr(self, key, value)
-        if key in ['host', 'port', 'path', 'protocol']:
-            key = 'url'
-            self.url = "%s://%s:%s%s" % (self.protocol, self.host,
-                                         self.port, self.path)
-            print "This option has been deprecated, please set 'url' instead"
-            print "This server url will be used:", self.url
-        write_config(self.get_attr, self.config_file)
-        read_config(self.get_attr, self.set_attr, self.config_file)
-        self.init_credential_store()
-        if key.strip() == 'profile' and self.interpreterMode:
-            print "\nLoaded server profile '%s' with options:" % value
-            for option in default_profile.keys():
-                value = self.get_attr(option)
-                if option in ["password", "apikey", "secretkey"] and value:
-                    value = value[:2] + "XXX" + value[4:6] + "YYY...(hidden)"
-                print "    %s = %s" % (option, value)
-            print
-
-    def complete_set(self, text, line, begidx, endidx):
-        mline = line.partition(" ")[2].lstrip().partition(" ")
-        option = mline[0].strip()
-        separator = mline[1]
-        value = mline[2].lstrip()
-        if separator == "":
-            return [s for s in self.config_options if s.startswith(option)] + self.completedefault(text, line, begidx, endidx)
-        elif option == "profile":
-            return [s for s in self.profile_names if s.startswith(value)]
-        elif option == "display":
-            return [s for s in display_types
-                    if s.startswith(value)]
-        elif option in ["asyncblock", "color", "paramcompletion",
-                        "verifysslcert"]:
-            return [s for s in ["true", "false"] if s.startswith(value)]
-        elif "set" in self.apicache["verbs"]:
-            return self.completedefault(text, line, begidx, endidx)
-
-        return []
-
-    def do_login(self, args):
-        """
-        Login using stored credentials. Starts a session to be reused for
-        subsequent api calls
-        """
-        try:
-            session, sessionkey = login(self.url, self.username, self.password)
-            self.credentials['session'] = session
-            self.credentials['sessionkey'] = sessionkey
-        except Exception, e:
-            self.monkeyprint("Error: Login failed to the server: ", unicode(e))
-
-    def do_logout(self, args):
-        """
-        Logout of session started with login with username and password
-        """
-        try:
-            logout(self.url, self.credentials.get('session'))
-        except Exception, e:
-            pass
-        self.credentials['session'] = None
-        self.credentials['sessionkey'] = None
-
-    def pipe_runner(self, args):
-        if args.find(" |") > -1:
-            pname = self.program_name
-            if '.py' in pname:
-                pname = "python " + pname
-            if isinstance(args, str):
-                self.do_shell("{0} {1}".format(pname, args))
-            else:
-                self.do_shell(u"{0} {1}".format(pname, args))
-            return True
-        return False
-
-    def do_shell(self, args):
-        """
-        Execute shell commands using shell <command> or !<command>
-
-        Example:
-        !ls
-        shell ls
-        !for((i=0; i<10; i++)); do cloudmonkey create user account=admin \
-            email=test@test.tt firstname=user$i lastname=user$i \
-            password=password username=user$i; done
-        """
-        if args.isdigit():
-            self.do_history("!" + args)
-            return
-        if isinstance(args, str):
-            os.system(args)
-        else:
-            os.system(args.encode("utf-8"))
-
-    def do_history(self, args):
-        """
-        Prints cloudmonkey history
-        """
-        if self.pipe_runner("history " + args):
-            return
-        startIdx = 1
-        endIdx = readline.get_current_history_length()
-        numLen = len(str(endIdx))
-        historyArg = args.split(' ')[0]
-        if historyArg.isdigit():
-            startIdx = endIdx - long(historyArg)
-            if startIdx < 1:
-                startIdx = 1
-        elif historyArg == "clear" or historyArg == "c":
-            readline.clear_history()
-            print "CloudMonkey history cleared"
-            return
-        elif len(historyArg) > 1 and historyArg[0] == "!" and historyArg[1:].isdigit():
-            command = readline.get_history_item(long(historyArg[1:]))
-            readline.set_startup_hook(lambda: readline.insert_text(command))
-            self.hook_count = 1
-            return
-        for idx in xrange(startIdx, endIdx):
-            self.monkeyprint("%s %s" % (str(idx).rjust(numLen),
-                                        readline.get_history_item(idx)))
-
-    def do_help(self, args):
-        """
-        Show help docs for various topics
-
-        Example:
-        help list
-        help list users
-        ?list
-        ?list users
-        """
-        fields = args.partition(" ")
-        if fields[2] == "":
-            cmd.Cmd.do_help(self, args)
-        else:
-            verb = fields[0]
-            subject = fields[2].partition(" ")[0]
-            if subject in self.apicache[verb]:
-                api = self.apicache[verb][subject]
-                helpdoc = "(%s) %s" % (api['name'], api['description'])
-                if api['isasync']:
-                    helpdoc += "\nThis API is asynchronous."
-                required = api['requiredparams']
-                if len(required) > 0:
-                    helpdoc += "\nRequired params are %s" % ' '.join(required)
-                helpdoc += "\nParameters\n" + "=" * 10
-                for param in api['params']:
-                    helpdoc += "\n%s = (%s) %s" % (
-                               param['name'], param['type'],
-                               param['description'])
-                self.monkeyprint(helpdoc)
-            else:
-                self.monkeyprint("Error: no such api (%s) on %s" %
-                                 (subject, verb))
-
-    def complete_help(self, text, line, begidx, endidx):
-        fields = line.partition(" ")
-        subfields = fields[2].partition(" ")
-
-        if subfields[1] != " ":
-            return cmd.Cmd.complete_help(self, text, line, begidx, endidx)
-        else:
-            line = fields[2]
-            text = subfields[2]
-            return self.completedefault(text, line, begidx, endidx)
-
-    def do_EOF(self, args):
-        """
-        Quit on Ctrl+d or EOF
-        """
-        self.do_logout(None)
-        sys.exit()
-
-    def do_exit(self, args):
-        """
-        Quit CloudMonkey CLI
-        """
-        return self.do_quit(args)
-
-    def do_quit(self, args):
-        """
-        Quit CloudMonkey CLI
-        """
-        self.monkeyprint("Bye!")
-        return self.do_EOF(args)
-
-
-def main():
-    parser = argparse.ArgumentParser(usage="cloudmonkey [options] [commands]",
-                                     description=__description__,
-                                     epilog="Try cloudmonkey [help|?]")
-
-    parser.add_argument("-v", "--version", action="version",
-                        default=argparse.SUPPRESS,
-                        version="cloudmonkey %s" % __version__,
-                        help="show CloudMonkey's version and exit")
-
-    parser.add_argument("-c", "--config-file",
-                        dest="configFile", default=config_file,
-                        help="config file for cloudmonkey", metavar="FILE")
-
-    parser.add_argument("-b", "--block-async", action="store_true",
-                        help="block and poll result on async API calls")
-
-    parser.add_argument("-n", "--noblock-async", action="store_true",
-                        help="do not block on async API calls")
-
-    parser.add_argument("-d", "--display-type",
-                        dest="displayType", default=None,
-                        help="output displays: json, xml, table or default",
-                        choices=tuple(display_types))
-
-    parser.add_argument("-p", "--profile",
-                        dest="serverProfile", default=None,
-                        help="server profile to load")
-
-    parser.add_argument("commands", nargs=argparse.REMAINDER,
-                        help="API commands")
-
-    argcomplete.autocomplete(parser)
-    args = parser.parse_args()
-
-    shell = CloudMonkeyShell(sys.argv[0], args.configFile)
-
-    if args.displayType and args.displayType in display_types:
-        shell.set_attr("display", args.displayType)
-
-    if args.noblock_async:
-        shell.set_attr("asyncblock", "false")
-
-    if args.block_async:
-        shell.set_attr("asyncblock", "true")
-
-    if args.serverProfile and args.serverProfile.strip() != '':
-        shell.do_set("profile %s" % args.serverProfile)
-
-    if len(args.commands) > 0:
-        shell.set_attr("color", "false")
-        commands = []
-        for command in args.commands:
-            split_command = command.split("=", 1)
-            if len(split_command) > 1:
-                key = split_command[0]
-                value = split_command[1]
-                if " " not in value or \
-                   (value.startswith("\"") and value.endswith("\"")) or \
-                   (value.startswith("\'") and value.endswith("\'")):
-                    commands.append(command)
-                else:
-                    commands.append("%s=\"%s\"" % (key, value))
-            else:
-                commands.append(command)
-        shell.onecmd(" ".join(commands))
-        if shell.error_on_last_command:
-            sys.exit(1)
-    else:
-        shell.cmdloop()
-
-    try:
-        sys.stdout.close()
-    except:
-        pass
-    try:
-        sys.stderr.close()
-    except:
-        pass
-
-
-if __name__ == "__main__":
-    main()
diff --git a/cloudmonkey/config.py b/cloudmonkey/config.py
deleted file mode 100644
index c5faec2..0000000
--- a/cloudmonkey/config.py
+++ /dev/null
@@ -1,209 +0,0 @@
-# -*- coding: utf-8 -*-
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-
-__version__ = "5.3.3"
-__description__ = "Command Line Interface for Apache CloudStack"
-__maintainer__ = "The Apache CloudStack Team"
-__maintaineremail__ = "dev@cloudstack.apache.org"
-__project__ = "The Apache CloudStack Team"
-__projectemail__ = "dev@cloudstack.apache.org"
-__projecturl__ = "http://cloudstack.apache.org"
-
-try:
-    import os
-    import sys
-
-    from ConfigParser import ConfigParser
-    from os.path import expanduser
-except ImportError, e:
-    print "ImportError", e
-
-param_type = ['boolean', 'date', 'float', 'integer', 'short', 'list',
-              'long', 'object', 'map', 'string', 'tzdate', 'uuid']
-
-iterable_type = ['set', 'list', 'object']
-
-# cloudmonkey display types
-display_types = ["json", "xml", "csv", "table", "default"]
-
-config_dir = expanduser('~/.cloudmonkey')
-config_file = expanduser(config_dir + '/config')
-
-# cloudmonkey config fields
-mandatory_sections = ['core', 'ui']
-default_profile_name = 'local'
-config_fields = {'core': {}, 'ui': {}}
-
-# core
-config_fields['core']['asyncblock'] = 'true'
-config_fields['core']['paramcompletion'] = 'true'
-config_fields['core']['cache_file'] = expanduser(config_dir + '/cache')
-config_fields['core']['history_file'] = expanduser(config_dir + '/history')
-config_fields['core']['log_file'] = expanduser(config_dir + '/log')
-config_fields['core']['profile'] = default_profile_name
-
-# ui
-config_fields['ui']['color'] = 'true'
-config_fields['ui']['prompt'] = '🐵 > '
-config_fields['ui']['display'] = 'default'
-
-# default profile
-default_profile = {}
-default_profile['url'] = 'http://localhost:8080/client/api'
-default_profile['timeout'] = '3600'
-default_profile['expires'] = '600'
-default_profile['username'] = 'admin'
-default_profile['password'] = 'password'
-default_profile['domain'] = '/'
-default_profile['apikey'] = ''
-default_profile['secretkey'] = ''
-default_profile['verifysslcert'] = 'true'
-default_profile['signatureversion'] = '3'
-
-
-def write_config(get_attr, config_file):
-    global config_fields, mandatory_sections
-    global default_profile, default_profile_name
-    config = ConfigParser()
-    if os.path.exists(config_file):
-        try:
-            with open(config_file, 'r') as cfg:
-                config.readfp(cfg)
-        except IOError, e:
-            print "Error: config_file not found", e
-
-    profile = None
-    try:
-        profile = get_attr('profile')
-    except AttributeError, e:
-        pass
-    if profile is None or profile == '':
-        profile = default_profile_name
-    if profile in mandatory_sections:
-        print "Server profile name cannot be '%s'" % profile
-        sys.exit(1)
-
-    has_profile_changed = False
-    profile_in_use = default_profile_name
-    try:
-        profile_in_use = config.get('core', 'profile')
-    except Exception:
-        pass
-    if profile_in_use != profile:
-        has_profile_changed = True
-
-    for section in (mandatory_sections + [profile]):
-        if not config.has_section(section):
-            try:
-                config.add_section(section)
-                if section not in mandatory_sections:
-                    for key in default_profile.keys():
-                        config.set(section, key, default_profile[key])
-                else:
-                    for key in config_fields[section].keys():
-                        config.set(section, key, config_fields[section][key])
-            except ValueError, e:
-                print "Server profile name cannot be", profile
-                sys.exit(1)
-        if section in mandatory_sections:
-            section_keys = config_fields[section].keys()
-        else:
-            section_keys = default_profile.keys()
-        for key in section_keys:
-            try:
-                if not (has_profile_changed and section == profile):
-                    config.set(section, key, get_attr(key))
-            except Exception:
-                pass
-    with open(config_file, 'w') as cfg:
-        config.write(cfg)
-    return config
-
-
-def read_config(get_attr, set_attr, config_file):
-    global config_fields, config_dir, mandatory_sections
-    global default_profile, default_profile_name
-    if not os.path.exists(config_dir):
-        os.makedirs(config_dir)
-
-    config_options = reduce(lambda x, y: x + y, map(lambda x:
-                            config_fields[x].keys(), config_fields.keys()))
-    config_options += default_profile.keys()
-
-    config = ConfigParser()
-    if os.path.exists(config_file):
-        try:
-            with open(config_file, 'r') as cfg:
-                config.readfp(cfg)
-        except IOError, e:
-            print "Error: config_file not found", e
-    else:
-        config = write_config(get_attr, config_file)
-        print "Welcome! Use the `set` command to configure options"
-        print "Config file:", config_file
-        print "After setting up, run the `sync` command to sync apis\n"
-
-    missing_keys = []
-    if config.has_option('core', 'profile'):
-        profile = config.get('core', 'profile')
-    else:
-        global default_profile_name
-        profile = default_profile_name
-
-    if profile is None or profile == '' or profile in mandatory_sections:
-        print "Server profile cannot be", profile
-        sys.exit(1)
-
-    set_attr("profile_names", filter(lambda x: x != "core" and x != "ui",
-                                     config.sections()))
-
-    if not config.has_section(profile):
-        print ("Selected profile (%s) does not exist," +
-               " using default values") % profile
-        try:
-            config.add_section(profile)
-        except ValueError, e:
-            print "Server profile name cannot be", profile
-            sys.exit(1)
-        for key in default_profile.keys():
-            config.set(profile, key, default_profile[key])
-
-    for section in (mandatory_sections + [profile]):
-        if section in mandatory_sections:
-            section_keys = config_fields[section].keys()
-        else:
-            section_keys = default_profile.keys()
-        for key in section_keys:
-            try:
-                set_attr(key, config.get(section, key))
-            except Exception, e:
-                if section in mandatory_sections:
-                    set_attr(key, config_fields[section][key])
-                else:
-                    set_attr(key, default_profile[key])
-                missing_keys.append("%s = %s" % (key, get_attr(key)))
-            # Cosmetic fix for prompt
-            if key == 'prompt':
-                set_attr(key, get_attr('prompt').strip() + " ")
-
-    if len(missing_keys) > 0:
-        print "Missing configuration was set using default values for keys:"
-        print "`%s` in %s" % (', '.join(missing_keys), config_file)
-        write_config(get_attr, config_file)
-
-    return config_options
diff --git a/cloudmonkey/precache.py b/cloudmonkey/precache.py
deleted file mode 100644
index ac7d880..0000000
--- a/cloudmonkey/precache.py
+++ /dev/null
@@ -1,19 +0,0 @@
-# -*- coding: utf-8 -*-
-# Auto-generated code by cachemaker.py
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-apicache = {u'authorize': {u'securitygroupingress': {u'name': u'authorizeSecurityGroupIngress', u'related': [u'authorizeSecurityGroupEgress'], u'isasync': True, u'params': [{u'name': u'projectid', u'required': False, u'related': [u'listProjectAccounts', u'listProjects', u'activateProject', u'createProject', u'updateProject'], u'length': 255, u'type': u'uuid', u'description': u'an optional project of the security group'}, {u'name': u'cidrlist', u'required': False, u'related': [], u'length [...]
\ No newline at end of file
diff --git a/cloudmonkey/printer.py b/cloudmonkey/printer.py
deleted file mode 100644
index 29d5903..0000000
--- a/cloudmonkey/printer.py
+++ /dev/null
@@ -1,124 +0,0 @@
-# -*- coding: utf-8 -*-
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-
-try:
-    from pygments import highlight
-    from pygments.console import ansiformat
-    from pygments.formatter import Formatter
-    from pygments.lexer import bygroups, RegexLexer
-    from pygments.token import *
-
-    import sys
-except ImportError, e:
-    print e
-
-
-MONKEY_COLORS = {
-    Token:          '',
-    Whitespace:     'reset',
-    Text:           'reset',
-
-    Name:           'green',
-    Operator:       'teal',
-    Operator.Word:  'lightgray',
-    String:         'purple',
-
-    Keyword:        '_red_',
-    Error:          'red',
-    Literal:        'yellow',
-    Number:         'blue',
-}
-
-
-def get_colorscheme():
-    return MONKEY_COLORS
-
-
-class MonkeyLexer(RegexLexer):
-    keywords = ['[a-z]*id', '"[a-z]*id"', '^[a-z A-Z]*:']
-    attributes = ['[Tt]rue', '[Ff]alse']
-    params = ['[a-z]*[Nn]ame', 'type', '[Ss]tate']
-
-    uuid_rgx = r'[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}'
-    date_rgx = r'[0-9]{4}-[0-9]{2}-[0-9]{2}T[0-9:]{8}[0-9+]{5}'
-
-    def makelistre(lis):
-        return r'(' + r'|'.join(lis) + r')'
-
-    tokens = {
-        'root': [
-            (r' ', Whitespace),
-            (date_rgx, Number),
-            (r'"' + date_rgx + r'"', Number),
-            (uuid_rgx, Literal),
-            (r'"' + uuid_rgx + r'"', Literal),
-            (r'(?:\b\d+\b(?:-\b\d+|%)?)', Number),
-            (r'^[-=]*\n', Operator.Word),
-            (r'Error', Error),
-            (makelistre(attributes), Literal),
-            (makelistre(params) + r'( = )(.*)', bygroups(Name, Operator,
-                                                         String)),
-            (makelistre(keywords), Keyword),
-            (makelistre(params), Name),
-            (r'(^[a-zA-Z]* )(=)', bygroups(Name, Operator)),
-            (r'\S+', Text),
-        ]
-    }
-
-    def analyse_text(text):
-        npos = text.find('\n')
-        if npos < 3:
-            return False
-        return text[0] == '[' and text[npos - 1] == ']'
-
-
-class MonkeyFormatter(Formatter):
-    def __init__(self, **options):
-        Formatter.__init__(self, **options)
-        self.colorscheme = get_colorscheme()
-
-    def format(self, tokensource, outfile):
-        return Formatter.format(self, tokensource, outfile)
-
-    def format_unencoded(self, tokensource, outfile):
-        for ttype, value in tokensource:
-            color = self.colorscheme.get(ttype)
-            while color is None:
-                ttype = ttype[:-1]
-                color = self.colorscheme.get(ttype)
-            if color:
-                spl = value.split('\n')
-                for line in spl[:-1]:
-                    if line:
-                        outfile.write(ansiformat(color, line))
-                    outfile.write('\n')
-                if spl[-1]:
-                    outfile.write(ansiformat(color, spl[-1]))
-            else:
-                outfile.write(value)
-
-
-def monkeyprint(text):
-    fmter = MonkeyFormatter()
-    lexer = MonkeyLexer()
-    lexer.encoding = 'utf-8'
-    fmter.encoding = 'utf-8'
-    if text.startswith("Error"):
-        highlight(text, lexer, fmter, sys.stderr)
-    else:
-        highlight(text, lexer, fmter, sys.stdout)
diff --git a/cloudmonkey/requester.py b/cloudmonkey/requester.py
deleted file mode 100644
index 914854f..0000000
--- a/cloudmonkey/requester.py
+++ /dev/null
@@ -1,335 +0,0 @@
-#!/usr/bin/python
-# -*- coding: utf-8 -*-
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-
-try:
-    import base64
-    import hashlib
-    import hmac
-    import itertools
-    import json
-    import requests
-    import ssl
-    import sys
-    import time
-    import urllib
-    import urllib2
-
-    from datetime import datetime, timedelta
-    from requests_toolbelt import SSLAdapter
-    from urllib2 import HTTPError, URLError
-except ImportError, e:
-    print "Import error in %s : %s" % (__name__, e)
-    import sys
-    sys.exit()
-
-
-# Disable HTTPS verification warnings.
-from requests.packages import urllib3
-urllib3.disable_warnings()
-
-
-def logger_debug(logger, message):
-    if logger is not None:
-        logger.debug(message)
-
-
-def writeError(msg):
-    sys.stderr.write(msg)
-    sys.stderr.write("\n")
-    sys.stderr.flush()
-
-
-def login(url, username, password, domain="/", verifysslcert=False):
-    """
-    Login and obtain a session to be used for subsequent API calls
-    Wrong username/password leads to HTTP error code 531
-    """
-    args = {}
-
-    args["command"] = 'login'
-    args["username"] = username
-    args["password"] = password
-    args["domain"] = domain
-    args["response"] = "json"
-
-    sessionkey = ''
-    session = requests.Session()
-    session.mount('https://', SSLAdapter(ssl.PROTOCOL_TLSv1))
-
-    try:
-        resp = session.post(url, params=args, verify=verifysslcert)
-    except requests.exceptions.ConnectionError, e:
-        writeError("Connection refused by server: %s" % e)
-        return None, None
-
-    if resp.status_code == 200:
-        sessionkey = resp.json()['loginresponse']['sessionkey']
-    elif resp.status_code == 405:
-        writeError("Method not allowed, unauthorized access on URL: %s" % url)
-        session = None
-        sessionkey = None
-    elif resp.status_code == 531:
-        writeError("Error authenticating at %s using username: %s"
-                   ", password: %s, domain: %s" % (url, username, password,
-                                                   domain))
-        session = None
-        sessionkey = None
-    else:
-        resp.raise_for_status()
-
-    return session, sessionkey
-
-
-def logout(url, session):
-    if not session:
-        return
-    session.get(url, params={'command': 'logout'})
-
-
-def make_request_with_password(command, args, logger, url, credentials,
-                               verifysslcert=False):
-    error = None
-    args = args.copy()
-    username = credentials['username']
-    password = credentials['password']
-    domain = credentials['domain']
-
-    if not (username and password):
-        error = "Username and password cannot be empty"
-        result = None
-        return result, error
-
-    tries = 0
-    retry = True
-
-    while tries < 2 and retry:
-        sessionkey = credentials.get('sessionkey')
-        session = credentials.get('session')
-        tries += 1
-
-        # obtain a valid session if not supplied
-        if not (session and sessionkey):
-            session, sessionkey = login(url, username, password, domain,
-                                        verifysslcert)
-            if not (session and sessionkey):
-                return None, 'Authentication failed'
-            credentials['session'] = session
-            credentials['sessionkey'] = sessionkey
-
-        args['sessionkey'] = sessionkey
-
-        # make the api call
-        resp = session.get(url, params=args, verify=verifysslcert)
-        result = resp.text
-        logger_debug(logger, "Response received: %s" % resp.text)
-
-        if resp.status_code == 200:  # success
-            retry = False
-            break
-        if resp.status_code == 401:  # sessionkey is wrong
-            credentials['session'] = None
-            credentials['sessionkey'] = None
-            continue
-
-        if resp.status_code != 200 and resp.status_code != 401:
-            error_message = resp.headers.get('X-Description')
-            if not error_message:
-                error_message = resp.text
-            error = "{0}: {1}".format(resp.status_code, error_message)
-            result = None
-            retry = False
-
-    return result, error
-
-
-def make_request(command, args, logger, url, credentials, expires,
-                 verifysslcert=False, signatureversion=3):
-    result = None
-    error = None
-
-    if not url.startswith('http'):
-        error = "Server URL should start with 'http' or 'https', " + \
-                "please check and fix the url"
-        return None, error
-
-    if not args:
-        args = {}
-
-    args = args.copy()
-    args["command"] = command
-    args["response"] = "json"
-    signatureversion = int(signatureversion)
-    if signatureversion >= 3:
-        args["signatureversion"] = signatureversion
-        if not expires:
-            expires = 600
-        expirationtime = datetime.utcnow() + timedelta(seconds=int(expires))
-        args["expires"] = expirationtime.strftime('%Y-%m-%dT%H:%M:%S+0000')
-
-    for key in args.keys():
-        value = args[key]
-        if isinstance(value, unicode):
-            value = value.encode("utf-8")
-        args[key] = value
-        if not key:
-            args.pop(key)
-
-    # try to use the apikey/secretkey method by default
-    # followed by trying to check if we're using integration port
-    # finally use the username/password method
-    if not credentials['apikey'] and not ("8096" in url):
-        try:
-            return make_request_with_password(command, args, logger, url,
-                                              credentials, verifysslcert)
-        except (requests.exceptions.ConnectionError, Exception), e:
-            return None, e
-
-    def sign_request(params, secret_key):
-        request = zip(params.keys(), params.values())
-        request.sort(key=lambda x: x[0].lower())
-        hash_str = "&".join(
-            ["=".join(
-                [r[0].lower(),
-                 urllib.quote_plus(str(r[1]), safe="*").lower()
-                 .replace("+", "%20").replace("%3A", ":")]
-            ) for r in request]
-        )
-        return base64.encodestring(hmac.new(secret_key, hash_str,
-                                   hashlib.sha1).digest()).strip()
-
-    args['apiKey'] = credentials['apikey']
-    args["signature"] = sign_request(args, credentials['secretkey'])
-
-    session = requests.Session()
-    session.mount('https://', SSLAdapter(ssl.PROTOCOL_TLSv1))
-
-    try:
-        response = session.get(url, params=args, verify=verifysslcert)
-        logger_debug(logger, "Request sent: %s" % response.url)
-        result = response.text
-
-        if response.status_code == 200:  # success
-            error = None
-        elif response.status_code == 401:      # auth issue
-            error = "401 Authentication error"
-        elif response.status_code != 200 and response.status_code != 401:
-            error = "{0}: {1}".format(response.status_code,
-                                      response.headers.get('X-Description'))
-    except requests.exceptions.ConnectionError, e:
-        return None, "Connection refused by server: %s" % e
-    except Exception, pokemon:
-        error = pokemon.message
-
-    logger_debug(logger, "Response received: %s" % result)
-    if error is not None:
-        logger_debug(logger, "Error: %s" % (error))
-        return result, error
-
-    return result, error
-
-
-def monkeyrequest(command, args, isasync, asyncblock, logger, url,
-                  credentials, timeout, expires, verifysslcert=False,
-                  signatureversion=3):
-    response = None
-    error = None
-    logger_debug(logger, "======== START Request ========")
-    logger_debug(logger, "Requesting command=%s, args=%s" % (command, args))
-    response, error = make_request(command, args, logger, url,
-                                   credentials, expires, verifysslcert,
-                                   signatureversion)
-
-    logger_debug(logger, "======== END Request ========\n")
-
-    if error is not None and not response:
-        return response, error
-
-    def process_json(response):
-        try:
-            response = json.loads(response, "utf-8")
-        except ValueError, e:
-            logger_debug(logger, "Error processing json: %s" % e)
-            writeError("Error processing json: %s" % e)
-            response = None
-            error = e
-        return response
-
-    response = process_json(response)
-    if not response or not isinstance(response, dict):
-        return response, error
-
-    m = list(v for v in response.keys() if 'response' in v.lower())
-    if not m:
-        return response, 'Invalid response received: %s' % response
-
-    isasync = isasync and (asyncblock == "true" or asyncblock == "True")
-    responsekey = filter(lambda x: 'response' in x, response.keys())[0]
-
-    if isasync and 'jobid' in response[responsekey]:
-        jobid = response[responsekey]['jobid']
-        command = "queryAsyncJobResult"
-        request = {'jobid': jobid}
-        if not timeout:
-            timeout = 3600
-        timeout = int(timeout)
-        cursor = itertools.cycle([u'|', u'/', u'-', u'\\'])
-        while timeout > 0:
-            interval = 2
-            while interval > 0:
-                sys.stdout.write(u"%s\r" % cursor.next())
-                sys.stdout.flush()
-                time.sleep(0.1)
-                interval -= 0.1
-            timeout = timeout - 2
-            logger_debug(logger, "Job %s to timeout in %ds" % (jobid, timeout))
-
-            response, error = make_request(command, request, logger, url,
-                                           credentials, expires, verifysslcert)
-            if error and not response:
-                return response, error
-
-            response = process_json(response)
-            responsekeys = filter(lambda x: 'response' in x, response.keys())
-
-            if len(responsekeys) < 1:
-                continue
-
-            result = response[responsekeys[0]]
-            if "errorcode" in result or "errortext" in result:
-                return response, error
-
-            jobstatus = result['jobstatus']
-            if jobstatus == 2:
-                jobresult = result["jobresult"]
-                error = "\rAsync job %s failed\nError %s, %s" % (
-                        jobid, jobresult["errorcode"], jobresult["errortext"])
-                return response, error
-            elif jobstatus == 1:
-                sys.stdout.write(u"\r \n")
-                sys.stdout.flush()
-                return response, error
-            elif jobstatus == 0:
-                pass  # Job in progress
-            else:
-                logger_debug(logger, "We should not arrive here!")
-                sys.stdout.flush()
-
-        error = "Error: Async query timeout occurred for jobid %s" % jobid
-
-    return response, error
diff --git a/config.docker b/config.docker
deleted file mode 100644
index 17c536a..0000000
--- a/config.docker
+++ /dev/null
@@ -1,25 +0,0 @@
-[core]
-profile = container
-asyncblock = true
-paramcompletion = true
-history_file = /cloudmonkey/history
-log_file = /cloudmonkey/log
-cache_file = /cloudmonkey/cache
-
-
-[ui]
-color = true
-prompt = >
-display = default
-
-[container]
-url = http://cloudstack:8080/client/api
-username = admin
-password = password
-apikey =
-secretkey =
-timeout = 3600
-expires = 600
-verifysslcert = false
-signatureversion = 3
-domain = /
\ No newline at end of file
diff --git a/docs/.gitignore b/docs/.gitignore
deleted file mode 100644
index e35d885..0000000
--- a/docs/.gitignore
+++ /dev/null
@@ -1 +0,0 @@
-_build
diff --git a/docs/Makefile b/docs/Makefile
deleted file mode 100644
index 681b3a3..0000000
--- a/docs/Makefile
+++ /dev/null
@@ -1,177 +0,0 @@
-# Makefile for Sphinx documentation
-#
-
-# You can set these variables from the command line.
-SPHINXOPTS    =
-SPHINXBUILD   = sphinx-build
-PAPER         =
-BUILDDIR      = build
-
-# User-friendly check for sphinx-build
-ifeq ($(shell which $(SPHINXBUILD) >/dev/null 2>&1; echo $$?), 1)
-$(error The '$(SPHINXBUILD)' command was not found. Make sure you have Sphinx installed, then set the SPHINXBUILD environment variable to point to the full path of the '$(SPHINXBUILD)' executable. Alternatively you can add the directory with the executable to your PATH. If you don't have Sphinx installed, grab it from http://sphinx-doc.org/)
-endif
-
-# Internal variables.
-PAPEROPT_a4     = -D latex_paper_size=a4
-PAPEROPT_letter = -D latex_paper_size=letter
-ALLSPHINXOPTS   = -d $(BUILDDIR)/doctrees $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) source
-# the i18n builder cannot share the environment and doctrees with the others
-I18NSPHINXOPTS  = $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) source
-
-.PHONY: help clean html dirhtml singlehtml pickle json htmlhelp qthelp devhelp epub latex latexpdf text man changes linkcheck doctest gettext
-
-help:
-	@echo "Please use \`make <target>' where <target> is one of"
-	@echo "  html       to make standalone HTML files"
-	@echo "  dirhtml    to make HTML files named index.html in directories"
-	@echo "  singlehtml to make a single large HTML file"
-	@echo "  pickle     to make pickle files"
-	@echo "  json       to make JSON files"
-	@echo "  htmlhelp   to make HTML files and a HTML help project"
-	@echo "  qthelp     to make HTML files and a qthelp project"
-	@echo "  devhelp    to make HTML files and a Devhelp project"
-	@echo "  epub       to make an epub"
-	@echo "  latex      to make LaTeX files, you can set PAPER=a4 or PAPER=letter"
-	@echo "  latexpdf   to make LaTeX files and run them through pdflatex"
-	@echo "  latexpdfja to make LaTeX files and run them through platex/dvipdfmx"
-	@echo "  text       to make text files"
-	@echo "  man        to make manual pages"
-	@echo "  texinfo    to make Texinfo files"
-	@echo "  info       to make Texinfo files and run them through makeinfo"
-	@echo "  gettext    to make PO message catalogs"
-	@echo "  changes    to make an overview of all changed/added/deprecated items"
-	@echo "  xml        to make Docutils-native XML files"
-	@echo "  pseudoxml  to make pseudoxml-XML files for display purposes"
-	@echo "  linkcheck  to check all external links for integrity"
-	@echo "  doctest    to run all doctests embedded in the documentation (if enabled)"
-
-clean:
-	rm -rf $(BUILDDIR)/*
-
-html:
-	$(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html
-	@echo
-	@echo "Build finished. The HTML pages are in $(BUILDDIR)/html."
-
-dirhtml:
-	$(SPHINXBUILD) -b dirhtml $(ALLSPHINXOPTS) $(BUILDDIR)/dirhtml
-	@echo
-	@echo "Build finished. The HTML pages are in $(BUILDDIR)/dirhtml."
-
-singlehtml:
-	$(SPHINXBUILD) -b singlehtml $(ALLSPHINXOPTS) $(BUILDDIR)/singlehtml
-	@echo
-	@echo "Build finished. The HTML page is in $(BUILDDIR)/singlehtml."
-
-pickle:
-	$(SPHINXBUILD) -b pickle $(ALLSPHINXOPTS) $(BUILDDIR)/pickle
-	@echo
-	@echo "Build finished; now you can process the pickle files."
-
-json:
-	$(SPHINXBUILD) -b json $(ALLSPHINXOPTS) $(BUILDDIR)/json
-	@echo
-	@echo "Build finished; now you can process the JSON files."
-
-htmlhelp:
-	$(SPHINXBUILD) -b htmlhelp $(ALLSPHINXOPTS) $(BUILDDIR)/htmlhelp
-	@echo
-	@echo "Build finished; now you can run HTML Help Workshop with the" \
-	      ".hhp project file in $(BUILDDIR)/htmlhelp."
-
-qthelp:
-	$(SPHINXBUILD) -b qthelp $(ALLSPHINXOPTS) $(BUILDDIR)/qthelp
-	@echo
-	@echo "Build finished; now you can run "qcollectiongenerator" with the" \
-	      ".qhcp project file in $(BUILDDIR)/qthelp, like this:"
-	@echo "# qcollectiongenerator $(BUILDDIR)/qthelp/ApacheCloudStackCloudMonkey.qhcp"
-	@echo "To view the help file:"
-	@echo "# assistant -collectionFile $(BUILDDIR)/qthelp/ApacheCloudStackCloudMonkey.qhc"
-
-devhelp:
-	$(SPHINXBUILD) -b devhelp $(ALLSPHINXOPTS) $(BUILDDIR)/devhelp
-	@echo
-	@echo "Build finished."
-	@echo "To view the help file:"
-	@echo "# mkdir -p $$HOME/.local/share/devhelp/ApacheCloudStackCloudMonkey"
-	@echo "# ln -s $(BUILDDIR)/devhelp $$HOME/.local/share/devhelp/ApacheCloudStackCloudMonkey"
-	@echo "# devhelp"
-
-epub:
-	$(SPHINXBUILD) -b epub $(ALLSPHINXOPTS) $(BUILDDIR)/epub
-	@echo
-	@echo "Build finished. The epub file is in $(BUILDDIR)/epub."
-
-latex:
-	$(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
-	@echo
-	@echo "Build finished; the LaTeX files are in $(BUILDDIR)/latex."
-	@echo "Run \`make' in that directory to run these through (pdf)latex" \
-	      "(use \`make latexpdf' here to do that automatically)."
-
-latexpdf:
-	$(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
-	@echo "Running LaTeX files through pdflatex..."
-	$(MAKE) -C $(BUILDDIR)/latex all-pdf
-	@echo "pdflatex finished; the PDF files are in $(BUILDDIR)/latex."
-
-latexpdfja:
-	$(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
-	@echo "Running LaTeX files through platex and dvipdfmx..."
-	$(MAKE) -C $(BUILDDIR)/latex all-pdf-ja
-	@echo "pdflatex finished; the PDF files are in $(BUILDDIR)/latex."
-
-text:
-	$(SPHINXBUILD) -b text $(ALLSPHINXOPTS) $(BUILDDIR)/text
-	@echo
-	@echo "Build finished. The text files are in $(BUILDDIR)/text."
-
-man:
-	$(SPHINXBUILD) -b man $(ALLSPHINXOPTS) $(BUILDDIR)/man
-	@echo
-	@echo "Build finished. The manual pages are in $(BUILDDIR)/man."
-
-texinfo:
-	$(SPHINXBUILD) -b texinfo $(ALLSPHINXOPTS) $(BUILDDIR)/texinfo
-	@echo
-	@echo "Build finished. The Texinfo files are in $(BUILDDIR)/texinfo."
-	@echo "Run \`make' in that directory to run these through makeinfo" \
-	      "(use \`make info' here to do that automatically)."
-
-info:
-	$(SPHINXBUILD) -b texinfo $(ALLSPHINXOPTS) $(BUILDDIR)/texinfo
-	@echo "Running Texinfo files through makeinfo..."
-	make -C $(BUILDDIR)/texinfo info
-	@echo "makeinfo finished; the Info files are in $(BUILDDIR)/texinfo."
-
-gettext:
-	$(SPHINXBUILD) -b gettext $(I18NSPHINXOPTS) $(BUILDDIR)/locale
-	@echo
-	@echo "Build finished. The message catalogs are in $(BUILDDIR)/locale."
-
-changes:
-	$(SPHINXBUILD) -b changes $(ALLSPHINXOPTS) $(BUILDDIR)/changes
-	@echo
-	@echo "The overview file is in $(BUILDDIR)/changes."
-
-linkcheck:
-	$(SPHINXBUILD) -b linkcheck $(ALLSPHINXOPTS) $(BUILDDIR)/linkcheck
-	@echo
-	@echo "Link check complete; look for any errors in the above output " \
-	      "or in $(BUILDDIR)/linkcheck/output.txt."
-
-doctest:
-	$(SPHINXBUILD) -b doctest $(ALLSPHINXOPTS) $(BUILDDIR)/doctest
-	@echo "Testing of doctests in the sources finished, look at the " \
-	      "results in $(BUILDDIR)/doctest/output.txt."
-
-xml:
-	$(SPHINXBUILD) -b xml $(ALLSPHINXOPTS) $(BUILDDIR)/xml
-	@echo
-	@echo "Build finished. The XML files are in $(BUILDDIR)/xml."
-
-pseudoxml:
-	$(SPHINXBUILD) -b pseudoxml $(ALLSPHINXOPTS) $(BUILDDIR)/pseudoxml
-	@echo
-	@echo "Build finished. The pseudo-XML files are in $(BUILDDIR)/pseudoxml."
diff --git a/docs/source/cloudmonkey.rst b/docs/source/cloudmonkey.rst
deleted file mode 100644
index 22bf625..0000000
--- a/docs/source/cloudmonkey.rst
+++ /dev/null
@@ -1,62 +0,0 @@
-cloudmonkey package
-===================
-
-Submodules
-----------
-
-cloudmonkey.cachemaker module
------------------------------
-
-.. automodule:: cloudmonkey.cachemaker
-    :members:
-    :undoc-members:
-    :show-inheritance:
-
-cloudmonkey.cloudmonkey module
-------------------------------
-
-.. automodule:: cloudmonkey.cloudmonkey
-    :members:
-    :undoc-members:
-    :show-inheritance:
-
-cloudmonkey.config module
--------------------------
-
-.. automodule:: cloudmonkey.config
-    :members:
-    :undoc-members:
-    :show-inheritance:
-
-cloudmonkey.precache module
----------------------------
-
-.. automodule:: cloudmonkey.precache
-    :members:
-    :undoc-members:
-    :show-inheritance:
-
-cloudmonkey.printer module
---------------------------
-
-.. automodule:: cloudmonkey.printer
-    :members:
-    :undoc-members:
-    :show-inheritance:
-
-cloudmonkey.requester module
-----------------------------
-
-.. automodule:: cloudmonkey.requester
-    :members:
-    :undoc-members:
-    :show-inheritance:
-
-
-Module contents
----------------
-
-.. automodule:: cloudmonkey
-    :members:
-    :undoc-members:
-    :show-inheritance:
diff --git a/docs/source/conf.py b/docs/source/conf.py
deleted file mode 100644
index 9c30ccb..0000000
--- a/docs/source/conf.py
+++ /dev/null
@@ -1,262 +0,0 @@
-# -*- coding: utf-8 -*-
-#
-# Apache CloudStack CloudMonkey documentation build configuration file, created by
-# sphinx-quickstart on Tue Sep 24 13:08:09 2013.
-#
-# This file is execfile()d with the current directory set to its
-# containing dir.
-#
-# Note that not all possible configuration values are present in this
-# autogenerated file.
-#
-# All configuration values have a default; values that are commented out
-# serve to show the default.
-
-import sys
-import os
-
-# If extensions (or modules to document with autodoc) are in another directory,
-# add these directories to sys.path here. If the directory is relative to the
-# documentation root, use os.path.abspath to make it absolute, like shown here.
-#sys.path.insert(0, os.path.abspath('.'))
-
-# -- General configuration ------------------------------------------------
-
-# If your documentation needs a minimal Sphinx version, state it here.
-#needs_sphinx = '1.0'
-
-# Add any Sphinx extension module names here, as strings. They can be
-# extensions coming with Sphinx (named 'sphinx.ext.*') or your custom
-# ones.
-extensions = [
-    'sphinx.ext.autodoc',
-    'sphinx.ext.coverage',
-    'sphinx.ext.viewcode',
-]
-
-# Add any paths that contain templates here, relative to this directory.
-templates_path = ['_templates']
-
-# The suffix of source filenames.
-source_suffix = '.rst'
-
-# The encoding of source files.
-#source_encoding = 'utf-8-sig'
-
-# The master toctree document.
-master_doc = 'index'
-
-# General information about the project.
-project = u'Apache CloudStack CloudMonkey'
-copyright = u'2012-2014, The Apache Software Foundation'
-
-# The version info for the project you're documenting, acts as replacement for
-# |version| and |release|, also used in various other places throughout the
-# built documents.
-#
-# The short X.Y version.
-version = '5.3.3'
-# The full version, including alpha/beta/rc tags.
-release = version
-
-# The language for content autogenerated by Sphinx. Refer to documentation
-# for a list of supported languages.
-#language = None
-
-# There are two options for replacing |today|: either, you set today to some
-# non-false value, then it is used:
-#today = ''
-# Else, today_fmt is used as the format for a strftime call.
-#today_fmt = '%B %d, %Y'
-
-# List of patterns, relative to source directory, that match files and
-# directories to ignore when looking for source files.
-exclude_patterns = []
-
-# The reST default role (used for this markup: `text`) to use for all
-# documents.
-#default_role = None
-
-# If true, '()' will be appended to :func: etc. cross-reference text.
-#add_function_parentheses = True
-
-# If true, the current module name will be prepended to all description
-# unit titles (such as .. function::).
-#add_module_names = True
-
-# If true, sectionauthor and moduleauthor directives will be shown in the
-# output. They are ignored by default.
-#show_authors = False
-
-# The name of the Pygments (syntax highlighting) style to use.
-pygments_style = 'sphinx'
-
-# A list of ignored prefixes for module index sorting.
-#modindex_common_prefix = []
-
-# If true, keep warnings as "system message" paragraphs in the built documents.
-#keep_warnings = False
-
-
-# -- Options for HTML output ----------------------------------------------
-
-# The theme to use for HTML and HTML Help pages.  See the documentation for
-# a list of builtin themes.
-html_theme = 'default'
-
-# Theme options are theme-specific and customize the look and feel of a theme
-# further.  For a list of options available for each theme, see the
-# documentation.
-#html_theme_options = {}
-
-# Add any paths that contain custom themes here, relative to this directory.
-#html_theme_path = []
-
-# The name for this set of Sphinx documents.  If None, it defaults to
-# "<project> v<release> documentation".
-#html_title = None
-
-# A shorter title for the navigation bar.  Default is the same as html_title.
-#html_short_title = None
-
-# The name of an image file (relative to this directory) to place at the top
-# of the sidebar.
-#html_logo = None
-
-# The name of an image file (within the static path) to use as favicon of the
-# docs.  This file should be a Windows icon file (.ico) being 16x16 or 32x32
-# pixels large.
-#html_favicon = None
-
-# Add any paths that contain custom static files (such as style sheets) here,
-# relative to this directory. They are copied after the builtin static files,
-# so a file named "default.css" will overwrite the builtin "default.css".
-html_static_path = ['_static']
-
-# Add any extra paths that contain custom files (such as robots.txt or
-# .htaccess) here, relative to this directory. These files are copied
-# directly to the root of the documentation.
-#html_extra_path = []
-
-# If not '', a 'Last updated on:' timestamp is inserted at every page bottom,
-# using the given strftime format.
-#html_last_updated_fmt = '%b %d, %Y'
-
-# If true, SmartyPants will be used to convert quotes and dashes to
-# typographically correct entities.
-#html_use_smartypants = True
-
-# Custom sidebar templates, maps document names to template names.
-#html_sidebars = {}
-
-# Additional templates that should be rendered to pages, maps page names to
-# template names.
-#html_additional_pages = {}
-
-# If false, no module index is generated.
-#html_domain_indices = True
-
-# If false, no index is generated.
-#html_use_index = True
-
-# If true, the index is split into individual pages for each letter.
-#html_split_index = False
-
-# If true, links to the reST sources are added to the pages.
-#html_show_sourcelink = True
-
-# If true, "Created using Sphinx" is shown in the HTML footer. Default is True.
-#html_show_sphinx = True
-
-# If true, "(C) Copyright ..." is shown in the HTML footer. Default is True.
-#html_show_copyright = True
-
-# If true, an OpenSearch description file will be output, and all pages will
-# contain a <link> tag referring to it.  The value of this option must be the
-# base URL from which the finished HTML is served.
-#html_use_opensearch = ''
-
-# This is the file name suffix for HTML files (e.g. ".xhtml").
-#html_file_suffix = None
-
-# Output file base name for HTML help builder.
-htmlhelp_basename = 'ApacheCloudStackCloudMonkeydoc'
-
-
-# -- Options for LaTeX output ---------------------------------------------
-
-latex_elements = {
-# The paper size ('letterpaper' or 'a4paper').
-#'papersize': 'letterpaper',
-
-# The font size ('10pt', '11pt' or '12pt').
-#'pointsize': '10pt',
-
-# Additional stuff for the LaTeX preamble.
-#'preamble': '',
-}
-
-# Grouping the document tree into LaTeX files. List of tuples
-# (source start file, target name, title,
-#  author, documentclass [howto/manual]).
-latex_documents = [
-  ('index', 'ApacheCloudStackCloudMonkey.tex', u'Apache CloudStack CloudMonkey Documentation',
-   u'The Apache Software Foundation', 'manual'),
-]
-
-# The name of an image file (relative to this directory) to place at the top of
-# the title page.
-#latex_logo = None
-
-# For "manual" documents, if this is true, then toplevel headings are parts,
-# not chapters.
-#latex_use_parts = False
-
-# If true, show page references after internal links.
-#latex_show_pagerefs = False
-
-# If true, show URL addresses after external links.
-#latex_show_urls = False
-
-# Documents to append as an appendix to all manuals.
-#latex_appendices = []
-
-# If false, no module index is generated.
-#latex_domain_indices = True
-
-
-# -- Options for manual page output ---------------------------------------
-
-# One entry per manual page. List of tuples
-# (source start file, name, description, authors, manual section).
-man_pages = [
-    ('index', 'apachecloudstackcloudmonkey', u'Apache CloudStack CloudMonkey Documentation',
-     [u'The Apache Software Foundation'], 1)
-]
-
-# If true, show URL addresses after external links.
-#man_show_urls = False
-
-
-# -- Options for Texinfo output -------------------------------------------
-
-# Grouping the document tree into Texinfo files. List of tuples
-# (source start file, target name, title, author,
-#  dir menu entry, description, category)
-texinfo_documents = [
-  ('index', 'ApacheCloudStackCloudMonkey', u'Apache CloudStack CloudMonkey Documentation',
-   u'The Apache Software Foundation', 'ApacheCloudStackCloudMonkey', 'One line description of project.',
-   'Miscellaneous'),
-]
-
-# Documents to append as an appendix to all manuals.
-#texinfo_appendices = []
-
-# If false, no module index is generated.
-#texinfo_domain_indices = True
-
-# How to display URL addresses: 'footnote', 'no', or 'inline'.
-#texinfo_show_urls = 'footnote'
-
-# If true, do not generate a @detailmenu in the "Top" node's menu.
-#texinfo_no_detailmenu = False
diff --git a/docs/source/index.rst b/docs/source/index.rst
deleted file mode 100644
index bbb18ed..0000000
--- a/docs/source/index.rst
+++ /dev/null
@@ -1,37 +0,0 @@
-Apache CloudStack CloudMonkey
-=============================
-
-The Apache CloudStack CloudMonkey is a command line interface (CLI) tool for CloudStack written in Python. cloudmonkey
-can be use both as an interactive shell and as a command line tool which simplifies CS configuration and management.
-
-**Features**
-
-#. Usable as a command line tool and interactive shell
-#. All commands are lowercase unlike API
-#. Api Discovery using sync feature, with build time api precaching for failsafe sync
-#. Raw api execution support
-#. Auto-completion via double <tab>
-#. Reverse search using Ctrl+R
-#. Emacs compatible keybindings
-#. Pipeable output
-#. Unix shell execution
-#. Support to handle async jobs using user defined blocking or non-blocking way
-#. Tabular or JSON output with filtering of table columns
-#. Colored output
-#. Api parameter value completion (based on predication, fuzzy results may fail sometimes)
-#. Use apikey and secretkey or username/password
-
-Instructions for working with CloudMonkey can be found here:
-
-https://cwiki.apache.org/confluence/display/CLOUDSTACK/CloudStack+cloudmonkey+CLI
-
-.. toctree::
-   :maxdepth: 2
-
-Indices and tables
-==================
-
-* :ref:`genindex`
-* :ref:`modindex`
-* :ref:`search`
-
diff --git a/docs/source/modules.rst b/docs/source/modules.rst
deleted file mode 100644
index 2b7efb5..0000000
--- a/docs/source/modules.rst
+++ /dev/null
@@ -1,7 +0,0 @@
-cloudmonkey
-===========
-
-.. toctree::
-   :maxdepth: 4
-
-   cloudmonkey
diff --git a/setup.cfg b/setup.cfg
deleted file mode 100644
index 649ed60..0000000
--- a/setup.cfg
+++ /dev/null
@@ -1,7 +0,0 @@
-[build_sphinx]
-source-dir = docs/source
-build-dir  = docs/build
-all_files  = 1
-
-[upload_sphinx]
-upload-dir = docs/build/html
diff --git a/setup.py b/setup.py
deleted file mode 100644
index 4422328..0000000
--- a/setup.py
+++ /dev/null
@@ -1,86 +0,0 @@
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements.  See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership.  The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License.  You may obtain a copy of the License at
-#
-#   http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied.  See the License for the
-# specific language governing permissions and limitations
-# under the License.
-
-try:
-    from setuptools import setup, find_packages
-except ImportError:
-    from distribute_setup import use_setuptools
-    use_setuptools()
-    from setuptools import setup, find_packages
-
-import sys
-
-from cloudmonkey import __version__, __description__
-from cloudmonkey import __maintainer__, __maintaineremail__
-from cloudmonkey import __project__, __projecturl__, __projectemail__
-
-requires = [
-              'Pygments>=1.5',
-              'argcomplete',
-              'dicttoxml',
-              'prettytable>=0.6',
-              'requests',
-              'requests-toolbelt',
-            ]
-
-try:
-    import readline
-except ImportError:
-    platform = str(sys.platform).lower()
-    if 'win32' in platform or 'win64' in platform:
-        requires.append('pyreadline')
-    else:
-        requires.append('readline')
-
-# Upgrade notes for 5.3.0
-print "If you're upgrading, run the following to enable parameter completion:"
-print "  cloudmonkey sync"
-print "  cloudmonkey set paramcompletion true"
-print "Parameter completion may fail, if the above is not run!"
-
-setup(
-    name = 'cloudmonkey',
-    version = __version__,
-    author = __project__,
-    author_email = __projectemail__,
-    maintainer = __maintainer__,
-    maintainer_email = __maintaineremail__,
-    url = __projecturl__,
-    description = __description__,
-    long_description = "cloudmonkey is a CLI for Apache CloudStack",
-    platforms = ("Any",),
-    license = 'ASL 2.0',
-    packages = find_packages(),
-    install_requires = requires,
-    include_package_data = True,
-    zip_safe = False,
-    classifiers = [
-        "Development Status :: 5 - Production/Stable",
-        "Environment :: Console",
-        "Intended Audience :: Developers",
-        "Intended Audience :: End Users/Desktop",
-        "Operating System :: OS Independent",
-        "Programming Language :: Python",
-        "Topic :: Software Development :: Testing",
-        "Topic :: Software Development :: Interpreters",
-        "Topic :: Utilities",
-    ],
-    entry_points="""
-    [console_scripts]
-    cloudmonkey = cloudmonkey.cloudmonkey:main
-    """,
-)

-- 
To stop receiving notification emails like this one, please contact
rohit@apache.org.