#! /usr/bin/env python
# -*- Mode: python; py-indent-offset: 4; tab-width: 8; -*-

"""
onoscli : ONOS-specific Command Line Interface

Usage:
    # Running the CLI in interactive mode:
    $ ./onoscli

    # Running multiple CLI commands in batch mode
    $ cat commands.txt | ./onoscli

    # Running a single command from the system command-line
    $ ./onoscli -c show switch all

    # Run the following command for additional help
    $ ./onoscli -h
"""

#
# INSTALLATION NOTES: MUST install Python cmd2 module. E.g., on Ubuntu:
#    sudo apt-get install python-cmd2
# On older Ubuntu installations (e.g., Ubuntu-12.04 or Ubuntu-13.04), install
# also:
#    sudo apt-get install python-pyparsing
#

#
# ADDING A NEW CLI COMMAND:
#  1. Add the appropriate Command entry (or entries) inside array
#     OnosCli.init_commands.
#     See the comments for init_commands for details.
#  2. Add the appropriate callback (inside class OnosCli) for the CLI command
#
#

import sys
import argparse
import json
from optparse import make_option
import urllib2
from urllib2 import URLError, HTTPError
import cmd2
from cmd2 import Cmd
from cmd2 import options


class Command():
    "Command node. A hierarchy of nodes are organized in a command tree."

    def __init__(self, name, help, callback=None, add_parser_args=None):
        """name: a string with the full command name
           help: the help string for the command
           callback: the method to be called if the command is executed
           add_parser_args: the parser arguments to add to the command: a dictionary of argparse arguments"""
        # Normalize the name by removing extra spaces
        self.split_name = name.split()  # List of the words in the name
        self.name = ' '.join(self.split_name)   # Normalized name
        self.last_subname = self.split_name[-1] # Last word in the name
        self.parent_name = ' '.join(self.split_name[:-1]) # Name of parent command
        self.help = help                # THe help string
        self.callback = callback        # The command callback
        self.add_parser_args = add_parser_args  # Parser arguments to add
        self.parent = None              # The parent Command
        self.children = []              # The children Command entries


class OnosCli(Cmd):
    "The main ONOS CLI class"

    # Setup generic CLI fields
    intro = "Welcome to the ONOS CLI. Type help or ? to list commands.\n"
    prompt = "(onos) "
    settable = Cmd.settable + "prompt CLI prompt"

    # Setup ONOS-specific fields
    onos_ip = "127.0.0.1"
    settable = settable + "onos_ip ONOS IP address"
    onos_port = 8080
    settable = settable + "onos_port ONOS REST port number"
    output_format = "json"      # Valid values: json, text
    settable = settable + "output_format The output format: `text` or `json`"

    # Collection of commands sorted by the level in the CLI command hierarchy
    commands = []
    # Commands, parsers and subparsers keyed by the command name
    commands_dict = {}
    parsers_dict = {}
    subparsers_dict = {}

    def __init__(self):
        Cmd.__init__(self)

        #
        # An array of the ONOS-specific CLI commands.
        # Each entry is a Command instance, and must have at least
        # two arguments:
        #  * Command name as typed on the CLI. E.g.:
        #    "show intent"
        #  * Command help description. E.g.:
        #    "Show intents"
        #
        # Executable commands should have a third Command argument, which is
        # the name of the method to be called when the command is executed.
        # The method will be called with the (argparse) parsed arguments
        # for that command.
        #
        # If an executable command takes arguments, those should be described
        # in the Command's fourth argument. It is a list of pairs:
        #   [
        #    ("--argument-name1", dict(...)),
        #    ("--argument-name2", dict(...)),
        #    ...
        #   ]
        # where the first entry in the pair is the argument name, and the
        # second entry in the pair is a dictionary with argparse-specific
        # description of the argument.
        #
        init_commands = [
            Command("delete", "Delete command"),
            #
            Command("delete intent",
                    """Delete high-level intents
    Usage:
      delete intent --intent-id INTENT_ID  Delete a high-level intent
      delete intent --all                  Delete all high-level intents
    Arguments:
      --intent-id INTENT_ID    The Intent ID (an integer)
      --all                    Delete all high-level intents""",
                    self.delete_intent,
                    [
                    ("--intent-id", dict(required=False, type=int)),
                    ("--all", dict(required=False, action='store_true'))
                    ]
                    ),
            #
            Command("set", "Set command"),
            #
            Command("set intent",
                    """Set a high-level intent
    Usage:
      set intent <ARGS>
    Arguments:
      --intent-id INTENT_ID     The Intent ID (an integer) (REQUIRED)
      --src-dpid SRC_DPID       Source Switch DPID (REQUIRED)
      --src-port SRC_PORT       Source Switch Port (REQUIRED)
      --dst-dpid DST_DPID       Destination Switch DPID (REQUIRED)
      --dst-port DST_PORT       Destination Switch Port (REQUIRED)
      --match-src-mac MATCH_SRC_MAC Matching Source MAC Address (REQUIRED)
      --match-dst-mac MATCH_DST_MAC Matching Destination MAC Address (REQUIRED)""",
                    self.set_intent,
                    [
                    ("--intent-id", dict(required=True, type=int)),
                    ("--src-dpid", dict(required=True)),
                    ("--src-port", dict(required=True, type=int)),
                    ("--dst-dpid", dict(required=True)),
                    ("--dst-port", dict(required=True, type=int)),
                    ("--match-src-mac", dict(required=True)),
                    ("--match-dst-mac", dict(required=True))
                    ]),
            #
            Command("show", "Show command"),
            #
            Command("show host", "Show hosts"),
            #
            Command("show host all", "Show all hosts", self.show_host_all),
            #
            Command("show intent", "Show intents"),
            #
            Command("show intent high",
                    """Show all high-level intents
  show intent high --intent-id INTENT_ID    Show a high-level intent""",
                    self.show_intent_high,
                    [
                    ("--intent-id", dict(required=False, type=int))
                    ]
                    ),
            #
            Command("show intent low",
                    """Show all low-level intents
  show intent low  --intent-id INTENT_ID    Show a low-level intent""",
                    self.show_intent_low,
                    [
                    ("--intent-id", dict(required=False))
                    ]
                    ),
            #
            Command("show link", "Show links"),
            #
            Command("show link all", "Show all links", self.show_link_all),
            #
            Command("show path", "Show a path"),
            #
            Command("show path shortest",
                    """Show a shortest path
    Usage:
      show path shortest --src-dpid SRC_DPID --dst-dpid DST_DPID
    Arguments:
      --src-dpid SRC_DPID       Source Switch DPID
      --dst-dpid DST_DPID       Destination Switch DPID""",
                    self.show_path_shortest,
                    [
                    ("--src-dpid", dict(required=True)),
                    ("--dst-dpid", dict(required=True))
                    ]),
            #
            Command("show switch", "Show switches"),
            #
            Command("show switch all", "Show all switches", self.show_switch_all),
            #
            Command("show topology", "Show network topology"),
            #
            Command("show topology all", "Show whole network topology", self.show_topology_all)
        ]

        # Sort the commands by the level in the CLI command hierarchy
        self.commands = sorted(init_commands, key = lambda c: len(c.name.split()))

        # Create a dictionary with all commands: name -> Command
        for c in self.commands:
            self.commands_dict[c.name] = c

        # Create a tree with all commands
        for c in self.commands:
            if c.parent_name:
                pc = self.commands_dict[c.parent_name]
                pc.children.append(c)
                c.parent = pc

        # Create the parsers and the sub-parsers
        for c in self.commands:
            # Add a parser
            parser = None
            if c.parent is None:
                # Add a top-level parser
                parser = argparse.ArgumentParser(description=c.help,
                                                 prog=c.name,
                                                 add_help=False)
            else:
                # Add a parser from the parent's subparser
                parent_subparser = self.subparsers_dict[c.parent_name]
                parser = parent_subparser.add_parser(c.last_subname,
                                                     help=c.help,
                                                     add_help=False)
            self.parsers_dict[c.name] = parser
            # Add a sub-parser
            if c.children:
                subparser = parser.add_subparsers(help=c.help)
                self.subparsers_dict[c.name] = subparser
            # Setup the callback
            if c.callback is not None:
                parser.set_defaults(func=c.callback)
            # Init the argument parser
            if c.add_parser_args is not None:
                for a in c.add_parser_args:
                    (p1, p2) = a
                    parser.add_argument(p1, **p2)

    def delete_intent(self, args):
        "CLI command callback: delete intent"

        url = ""
        if args.all:
            # Delete all intents
            url = "http://%s:%s/wm/onos/intent/high" % (self.onos_ip, self.onos_port)
        else:
            if args.intent_id is None:
                print "*** Unknown syntax:"
                self.help_delete()
                return;
            # Delete an intent
            url = "http://%s:%s/wm/onos/intent/high/%s" % (self.onos_ip, self.onos_port, args.intent_id)

        result = delete_json(url)
        # NOTE: No need to print the response
        # if len(result) != 0:
        #     self.print_json_result(result)

    def set_intent(self, args):
        "CLI command callback: set intent"

        intents = []
        oper = {}
        # Create the POST payload
        oper['intentId'] = args.intent_id
        oper['intentType'] = 'SHORTEST_PATH'    # XXX: Hardcoded
        oper['staticPath'] = False              # XXX: Hardcoded
        oper['srcSwitchDpid'] = args.src_dpid
        oper['srcSwitchPort'] = args.src_port
        oper['dstSwitchDpid'] = args.dst_dpid
        oper['dstSwitchPort'] = args.dst_port
        oper['matchSrcMac'] = args.match_src_mac
        oper['matchDstMac'] = args.match_dst_mac
        intents.append(oper)

        url = "http://%s:%s/wm/onos/intent/high" % (self.onos_ip, self.onos_port)
        result = post_json(url, intents)
        # NOTE: No need to print the response
        # if len(result) != 0:
        #     self.print_json_result(result)

    def show_host_all(self, args):
        "CLI command callback: show host all"

        url = "http://%s:%s/wm/onos/topology/hosts" % (self.onos_ip, self.onos_port)
        result = get_json(url)
        self.print_json_result(result)

    def show_intent_high(self, args):
        "CLI command callback: show intent high"

        if args.intent_id is None:
            # Show all intents
            url = "http://%s:%s/wm/onos/intent/high" % (self.onos_ip, self.onos_port)
        else:
            # Show a single intent
            url = "http://%s:%s/wm/onos/intent/high/%s" % (self.onos_ip, self.onos_port, args.intent_id)

        result = get_json(url)
        self.print_json_result(result)

    def show_intent_low(self, args):
        "CLI command callback: show intent low"

        if args.intent_id is None:
            # Show all intents
            url = "http://%s:%s/wm/onos/intent/low" % (self.onos_ip, self.onos_port)
        else:
            # Show a single intent
            url = "http://%s:%s/wm/onos/intent/low/%s" % (self.onos_ip, self.onos_port, args.intent_id)

        result = get_json(url)
        self.print_json_result(result)

    def show_link_all(self, args):
        "CLI command callback: show link all"

        url = "http://%s:%s/wm/onos/topology/links" % (self.onos_ip, self.onos_port)
        result = get_json(url)
        #
        if (self.output_format == "json"):
            self.print_json_result(result)
        else:
            # NOTE: The code below is for demo purpose only how to
            # decode and print the links in text format. It will be
            # reimplemented in the future.
            links = result
            print "# src_dpid src_port -> dst_dpid dst_port"
            for v in sorted(links, key=lambda x: x['src-switch']):
                if v.has_key('dst-switch'):
                    dst_dpid = str(v['dst-switch'])
                if v.has_key('src-switch'):
                    src_dpid = str(v['src-switch'])
                if v.has_key('src-port'):
                    src_port = str(v['src-port'])
                if v.has_key('dst-port'):
                    dst_port = str(v['dst-port'])
                self.print_result("%s %s -> %s %s" % (src_dpid, src_port, dst_dpid, dst_port))

    def show_path_shortest(self, args):
        "CLI command callback: show path shortest"

        url = "http://%s:%s/wm/onos/intent/path/switch/%s/shortest-path/%s" % (self.onos_ip, self.onos_port, args.src_dpid, args.dst_dpid)
        result = get_json(url)
        #
        self.print_json_result(result)

    def show_switch_all(self, args):
        "CLI command callback: show switch all"

        url = "http://%s:%s/wm/onos/topology/switches" % (self.onos_ip, self.onos_port)
        result = get_json(url)
        #
        self.print_json_result(result)

    def show_topology_all(self, args):
        "CLI command callback: show topology all"

        url = "http://%s:%s/wm/onos/topology" % (self.onos_ip, self.onos_port)
        result = get_json(url)
        #
        self.print_json_result(result)

    #
    # Implement "delete" top-level command
    #
    def do_delete(self, arg):
        "Top-level 'delete' command"
        self.impl_do_command('delete', arg)
    def complete_delete(self, text, line, begidx, endidx):
        "Completion of top-level 'delete' command"
        return self.impl_complete_command('delete', text, line, begidx, endidx)
    def help_delete(self):
        "Help for top-level 'delete' command"
        self.impl_help_command('delete')

    #
    # Implement "set" top-level command
    #
    def do_set(self, arg):
        "Top-level 'set' command"
        self.impl_do_command('set', arg)
    def complete_set(self, text, line, begidx, endidx):
        "Completion of top-level 'set' command"
        return self.impl_complete_command('set', text, line, begidx, endidx)
    def help_set(self):
        "Help for top-level 'set' command"
        self.impl_help_command('set')

    #
    # Implement "show" top-level command
    #
    def do_show(self, arg):
        "Top-level 'show' command"
        self.impl_do_command('show', arg)
    def complete_show(self, text, line, begidx, endidx):
        "Completion of top-level 'show' command"
        return self.impl_complete_command('show', text, line, begidx, endidx)
    def help_show(self):
        "Help for top-level 'show' command"
        self.impl_help_command('show')

    #
    # Implement the "do_something" top-level command execution
    #
    def impl_do_command(self, root_name, arg):
        "Implementation of top-level 'do_something' command execution"
        parser = self.parsers_dict[root_name]
        parsed_args = parser.parse_args(arg.split())
        parsed_args.func(parsed_args)

    #
    # Implement the "complete_something" top-level command completion
    #
    def impl_complete_command(self, root_name, text, line, begidx, endidx):
        "Implementation of top-level 'complete_something' command completion"
        root_command = self.commands_dict[root_name]
        subtree_commands = self.collect_subtree_commands(root_command)

        #
        # Loop through the commands and add their portion
        # of the sub-name to the list of completions.
        #
        # NOTE: We add a command only if it has a callback.
        #
        completions = []
        for c in subtree_commands:
            if c.callback is None:
                continue
            name = c.split_name[len(root_command.split_name):]
            completions.append(' '.join(name))

        mline = line.partition(" ")[2]
        offs = len(mline) - len(text)
        return [s[offs:] for s in completions if s.startswith(mline)]

    #
    # Implement the "help_something" top-level command help
    #
    def impl_help_command(self, root_name):
        "Implementation of top-level 'help_something' command help"
        root_command = self.commands_dict[root_name]
        subtree_commands = self.collect_subtree_commands(root_command)

        #
        # Loop through the commands and print the help for each command.
        # NOTE: We add a command only if it has a callback.
        #
        print "Help for the `%s` command:" % (root_name)
        for c in subtree_commands:
            if c.callback is None:
                continue
            print "  {0:30}{1:30}".format(c.name, c.help)
            # if c.init_arg_parser is not None:
            #   parser = self.parsers_dict[c.name]
            #   parser.print_help()

    #
    # Traverse (breadth-first) a subtree and return all nodes except the
    # root node.
    #
    def collect_subtree_commands(self, root_command):
        """Collect a subtree of commands.
           Traverses (breadth-first) a subtree of commands and returns
           all nodes except the root node."""

        commands = []
        subtree_commands = []
        commands.append(root_command)
        # Use breadth-first to traverse the subtree
        while commands:
            pc = commands.pop(0)
            for c in pc.children:
                commands.append(c)
                subtree_commands.append(c)
        return subtree_commands

    def log_debug(self, msg):
        """Log debug information.
        msg: the message to log
        Use the following CLI commands to enable/disable debugging:
          paramset debug true
          paramset debug false
        """
        if self.debug:
            print "%s" % (msg)

    def print_json_result(self, json_result):
        """Print JSON result."""
        if len(json_result) == 0:
            return
        result = json.dumps(json_result, indent=4)
        self.print_result(result)

    def print_result(self, result):
        """Print parsed result."""
        print "%s" % (result)

    #
    # Implementation of the "paramshow" CLI command.
    #
    # NOTE: The do_paramshow implementation below is copied from
    # the cmd2.do_show() implementation
    #
    @options([make_option('-l', '--long', action="store_true",
                 help="describe function of parameter")])
    def do_paramshow(self, arg, opts):
        '''Shows value of a parameter.'''
        param = arg.strip().lower()
        result = {}
        maxlen = 0
        for p in self.settable:
            if (not param) or p.startswith(param):
                result[p] = '%s: %s' % (p, str(getattr(self, p)))
                maxlen = max(maxlen, len(result[p]))
        if result:
            for p in sorted(result):
                if opts.long:
                    self.poutput('%s # %s' % (result[p].ljust(maxlen), self.settable[p]))
                else:
                    self.poutput(result[p])
        else:
            raise NotImplementedError("Parameter '%s' not supported (type 'show' for list of parameters)." % param)

    #
    # Implementation of the "paramset" CLI command.
    #
    #
    # NOTE: The do_paramset implementation below is copied from
    # the cmd2.do_set() implementation (with minor modifications).
    #
    def do_paramset(self, arg):
        '''
        Sets a cmd2 parameter.  Accepts abbreviated parameter names so long
        as there is no ambiguity.  Call without arguments for a list of
        settable parameters with their values.'''

        class NotSettableError(Exception):
            pass

        try:
            statement, paramName, val = arg.parsed.raw.split(None, 2)
            val = val.strip()
            paramName = paramName.strip().lower()
            if paramName not in self.settable:
                hits = [p for p in self.settable if p.startswith(paramName)]
                if len(hits) == 1:
                    paramName = hits[0]
                else:
                    return self.do_paramshow(paramName)
            currentVal = getattr(self, paramName)
            if (val[0] == val[-1]) and val[0] in ("'", '"'):
                val = val[1:-1]
            else:
                val = cmd2.cast(currentVal, val)
            setattr(self, paramName, val)
            self.stdout.write('%s - was: %s\nnow: %s\n' % (paramName, currentVal, val))
            if currentVal != val:
                try:
                    onchange_hook = getattr(self, '_onchange_%s' % paramName)
                    onchange_hook(old=currentVal, new=val)
                except AttributeError:
                    pass
        except (ValueError, AttributeError, NotSettableError) as exc:
            self.do_paramshow(arg)


def get_json(url):
    """Make a REST GET call and return the JSON result
       url: the URL to call"""

    parsed_result = []
    try:
        response = urllib2.urlopen(url)
        result = response.read()
        response.close()
        if len(result) != 0:
            parsed_result = json.loads(result)
    except HTTPError as exc:
        print "ERROR:"
        print "  REST GET URL: %s" % url
        # NOTE: exc.fp contains the object with the response payload
        error_payload = json.loads(exc.fp.read())
        print "  REST Error Code: %s" % (error_payload['code'])
        print "  REST Error Summary: %s" % (error_payload['summary'])
        print "  REST Error Description: %s" % (error_payload['formattedDescription'])
        print "  HTTP Error Code: %s" % exc.code
        print "  HTTP Error Reason: %s" % exc.reason
    except URLError as exc:
        print "ERROR:"
        print "  REST GET URL: %s" % url
        print "  URL Error Reason: %s" % exc.reason
    return parsed_result

def post_json(url, data):
    """Make a REST POST call and return the JSON result
       url: the URL to call
       data: the data to POST"""

    parsed_result = []
    data_json = json.dumps(data)
    try:
        request = urllib2.Request(url, data_json)
        request.add_header("Content-Type", "application/json")
        response = urllib2.urlopen(request)
        result = response.read()
        response.close()
        if len(result) != 0:
            parsed_result = json.loads(result)
    except HTTPError as exc:
        print "ERROR:"
        print "  REST POST URL: %s" % url
        # NOTE: exc.fp contains the object with the response payload
        error_payload = json.loads(exc.fp.read())
        print "  REST Error Code: %s" % (error_payload['code'])
        print "  REST Error Summary: %s" % (error_payload['summary'])
        print "  REST Error Description: %s" % (error_payload['formattedDescription'])
        print "  HTTP Error Code: %s" % exc.code
        print "  HTTP Error Reason: %s" % exc.reason
    except URLError as exc:
        print "ERROR:"
        print "  REST POST URL: %s" % url
        print "  URL Error Reason: %s" % exc.reason
    return parsed_result

def delete_json(url):
    """Make a REST DELETE call and return the JSON result
       url: the URL to call"""

    parsed_result = []
    try:
        request = urllib2.Request(url)
        request.get_method = lambda: 'DELETE'
        response = urllib2.urlopen(request)
        result = response.read()
        response.close()
        if len(result) != 0:
            parsed_result = json.loads(result)
    except HTTPError as exc:
        print "ERROR:"
        print "  REST DELETE URL: %s" % url
        # NOTE: exc.fp contains the object with the response payload
        error_payload = json.loads(exc.fp.read())
        print "  REST Error Code: %s" % (error_payload['code'])
        print "  REST Error Summary: %s" % (error_payload['summary'])
        print "  REST Error Description: %s" % (error_payload['formattedDescription'])
        print "  HTTP Error Code: %s" % exc.code
        print "  HTTP Error Reason: %s" % exc.reason
    except URLError as exc:
        print "ERROR:"
        print "  REST DELETE URL: %s" % url
        print "  URL Error Reason: %s" % exc.reason
    return parsed_result

if __name__ == '__main__':
    onosCli = OnosCli()

    # Setup the parser
    parser = argparse.ArgumentParser()
    parser.add_argument('-c', '--command', nargs=argparse.REMAINDER,
                        help="Run arguments to the end of the line as a CLI command")
    parser.add_argument('--onos-ip',
                        help="Set the ONOS IP address (for REST calls)")
    parser.add_argument('--onos-port',
                        help="Set the ONOS port number (for REST calls)")
    parser.add_argument('-t', '--test', nargs='+',
                        help="Test against transcript(s) in FILE (wildcards OK)")

    # Parse the arguments
    parsed_args = parser.parse_args()
    if parsed_args.onos_ip:
        onosCli.onos_ip = parsed_args.onos_ip
    if parsed_args.onos_port:
        onosCli.onos_port = parsed_args.onos_port
    #
    # NOTE: We have to reset the command-line options so the Cmd2 parser
    # doesn't process them again.
    #
    sys.argv = [sys.argv[0]]

    # Run the CLI as appropriate
    if parsed_args.test:
        # Run CLI Transcript Tests
        onosCli.runTranscriptTests(parsed_args.test)
    elif  parsed_args.command:
        # Run arguments as a CLI command
        command_line = ' '.join(parsed_args.command)
        onosCli.onecmd(command_line)
    else:
        # Run interactive CLI
        onosCli.cmdloop()
