#!/usr/bin/env python

r"""
See help text for details (--help or -h option)..

Example properties file content:
quiet=n
test_mode=y
pos=file1 file2 file3

Example call:

prop_call.py --prop_file_name=prop_file my_program

The result is that the following command will be run:
my_program --test_mode=y --quiet=n file1 file2 file3
"""

import sys
import os

save_path_0 = sys.path[0]
del sys.path[0]

from gen_arg import *
from gen_print import *
from gen_valid import *
from gen_misc import *
from gen_cmd import *

# Restore sys.path[0].
sys.path.insert(0, save_path_0)


parser = argparse.ArgumentParser(
    usage='%(prog)s [OPTIONS]',
    description="%(prog)s will call a program using parameters retrieved" +
    " from the given properties file.",
    formatter_class=argparse.ArgumentDefaultsHelpFormatter,
    prefix_chars='-+')

parser.add_argument(
    '--prop_dir_path',
    default=os.environ.get("PROP_DIR_PATH", os.getcwd()),
    help='The path to the directory that contains the properties file.' +
    '  The default value is environment variable "PROP_DIR_PATH", if' +
    ' set.  Otherwise, it is the current working directory.')

parser.add_argument(
    '--prop_file_name',
    help='The path to a properties file that contains the parameters to' +
    ' pass to the program.  If the properties file has a ".properties"' +
    ' extension, the caller need not specify the extension.  The format' +
    ' of each line in the properties file should be as follows:' +
    ' <parm_name=parm_value>.  Do not quote the parm value.  To specify' +
    ' positional parms, use a parm name of "pos".  For example: pos=this'
    ' value')

parser.add_argument(
    'program_name',
    help='The name of the program to be run.')

# Populate stock_list with options we want.
stock_list = [("test_mode", 0), ("quiet", 1), ("debug", 0)]


def exit_function(signal_number=0,
                  frame=None):

    r"""
    Execute whenever the program ends normally or with the signals that we
    catch (i.e. TERM, INT).
    """

    dprint_executing()
    dprint_var(signal_number)

    qprint_pgm_footer()


def signal_handler(signal_number,
                   frame):

    r"""
    Handle signals.  Without a function to catch a SIGTERM or SIGINT, our
    program would terminate immediately with return code 143 and without
    calling our exit_function.
    """

    # Our convention is to set up exit_function with atexit.register() so
    # there is no need to explicitly call exit_function from here.

    dprint_executing()

    # Calling exit prevents us from returning to the code that was running
    # when we received the signal.
    exit(0)


def validate_parms():

    r"""
    Validate program parameters, etc.  Return True or False (i.e. pass/fail)
    accordingly.
    """

    global prop_dir_path
    global prop_file_path

    if not valid_dir_path(prop_dir_path):
        return False
    prop_dir_path = add_trailing_slash(prop_dir_path)

    if not valid_value(prop_file_name):
        return False

    prop_file_path = prop_dir_path + prop_file_name

    # If properties file is not found, try adding ".properties" extension.
    if not os.path.isfile(prop_file_path):
        alt_prop_file_path = prop_file_path + ".properties"
        if os.path.isfile(alt_prop_file_path):
            prop_file_path = alt_prop_file_path

    if not valid_file_path(prop_file_path):
        return False

    if not valid_value(program_name):
        return False

    gen_post_validation(exit_function, signal_handler)

    return True


def main():

    if not gen_get_options(parser, stock_list):
        return False

    if not validate_parms():
        return False

    qprint_pgm_header()

    # Get the parameters from the properties file.
    properties = my_parm_file(prop_file_path)
    # The parms (including program name) need to go into a list.
    parms = [program_name]
    for key, value in properties.items():
        if key == "pos":
            # Process positional parm(s).
            parms.extend(value.split())
        else:
            parms.append("--" + key + "=" + escape_bash_quotes(value))

    # parm_string is only created for display in non-quiet mode.
    parm_string = " ".join(parms[1:])
    cmd_buf = program_name + " " + parm_string
    qprint_issuing(cmd_buf)
    if not test_mode:
        os.execvp(program_name, parms)

    return True


# Main

if not main():
    exit(1)
