"""
This module contains the methods for the ``openxc-control`` command line
program.

`main` is executed when ``openxc-control`` is run, and all other callables in
this module are internal only.
"""
from __future__ import absolute_import

import argparse
import sys

from openxc.formats.json import JsonFormatter
from .common import device_options, configure_logging, select_device


def version(controller):
    print("Device is running version %s" % controller.version())


def reset(controller):
    print("Resetting device...")
    controller.reset()
    version(controller)


def write_file(controller, filename):
    with open(filename, "r") as output_file:
        corrupt_entries = 0
        message_count = 0
        for line in output_file:
            try:
                parsed_message = JsonFormatter.deserialize(line)
                if not isinstance(parsed_message, dict):
                    raise ValueError()
            except ValueError:
                corrupt_entries += 1
            else:
                message_count += 1
                controller.write(parsed_message['name'],
                        parsed_message['value'], parsed_message['event'])
        print("%d lines sent" % message_count)
        if corrupt_entries > 0:
            print("%d invalid lines in the data file were not sent" %
                    corrupt_entries)


def write(controller, name, value, event):
    print("Sending command %s: %s %s" % (name, value, event))
    controller.write(name, value, event)
    print("Done.")


def parse_options():
    parser = argparse.ArgumentParser(description="Send control messages to an "
            "attached OpenXC CAN translator", parents=[device_options()])
    parser.add_argument("command", type=str,
            choices=['version', 'reset', 'write'])
    write_group = parser.add_mutually_exclusive_group()
    write_group.add_argument("--name", action="store", dest="write_name",
            help="name for message write request")
    parser.add_argument("--value", action="store", dest="write_value",
            help="value for message write request")
    parser.add_argument("--event", action="store", dest="write_event",
            help="optional event for message write request")
    write_group.add_argument("-f", "--file", action="store",
            dest="write_input_file",
            help="path to a file with a list of message requests")

    return parser.parse_args()


def main():
    configure_logging()
    arguments = parse_options()

    controller_class, controller_kwargs = select_device(arguments)
    controller = controller_class(**controller_kwargs)

    if arguments.command == "version":
        version(controller)
    elif arguments.command == "reset":
        reset(controller)
    elif arguments.command == "write":
        if arguments.write_name:
            if not arguments.write_value:
                sys.exit("'write' requires a name and value or filename")
            write(controller, arguments.write_name, arguments.write_value,
                    arguments.write_event)
        elif not arguments.write_input_file:
            sys.exit("'write' requires a name and value or filename")
        else:
            write_file(controller, arguments.write_input_file)
    else:
        print("Unrecognized command \"%s\"" % arguments.command)

@@ -2071,16 +2071,23 @@
   help=%22
+option 
 value fo
@@ -2843,124 +2843,8 @@
 me:%0A
-            if not arguments.write_value:%0A                sys.exit(%22'write' requires a name and value or filename%22)%0A
     
@@ -2970,20 +2970,16 @@
    elif 
-not 
 argument
@@ -3014,141 +3014,140 @@
     
-sys.exit(%22'write' requires a name and value or filename%22)%0A        else:%0A            write_file(controller, arguments.write_input_file
+write_file(controller, arguments.write_input_file)%0A        else:%0A            sys.exit(%22'write' requires at least a name or filename%22
 )%0A  

Make value optional for commands, e.g. initialization commands.