# ----------------------------------------------------------------------
# Robot Parallel runner in docker containers
#
# Assumptions:
# - Executing on a linux vm with all pre-needed software installed
# - Docker container called "robotfwk" already pre-built
# Command line parameters:
# - executionfile : Path to a file containing what to execute
# - suitebase : Path to parent directory containing all suites
# - outputbase : Path to root directory of all outputs
# - maxsuites : Number of max suites to execute in parallel
# ----------------------------------------------------------------------

import argparse
import os.path
import sys
from accelarobotkeywords.runner.parallelrunner import ParallelRunner

def is_true(value) -> bool:
    return value is not None and str(value).strip().upper() == "TRUE"

def main():
    parser = argparse.ArgumentParser(description='Required command line parameters')
    parser.add_argument("-s", "--executionfile", type=str, required=True, help="Path of json file of what to execute")
    parser.add_argument("-b", "--suitebase", type=str, required=True, help="Base path for all suites")
    parser.add_argument("-o", "--outputbase", type=str, required=True, help="Path to outputs root directory")
    parser.add_argument("-m", "--maxsuites", type=int, required=True, help="Max suites to execute at same time")
    parser.add_argument("-p", "--tags", type=str, required=True, help="Robot tags to filter tests to be executed")
    parser.add_argument("-r", "--reporttitle", type=str, required=True, help="Custom Report Title")
    parser.add_argument("-d", "--devmode", type=int, required=False, help="Optional - Is this a dev run")
    parser.add_argument("-t", "--testsuite", type=str, required=False, help="Optional - The single testsuite name")
    parser.add_argument("-l", "--testcases", type=str, required=False, help="Optional - The list of test cases")
    parser.add_argument("-a", "--agency", type=str, required=True, help="Optional - The agency name")
    parser.add_argument("-v", "--civicplatformversion", type=str, required=False, help="Optional - civic platform version")
    parser.add_argument("-e", "--testrailresultenabled", type=str, required=False, help="Optional - test rail result enabled")
    parser.add_argument("-n", "--reruntests", type=int, required=False, help="Optional - rerun test as needed")
    parser.add_argument("-tp", "--testrailprojectid", type=int, required=False, help="Optional - test rail project id")
    parser.add_argument("-ts", "--testrailsuiteid", type=int, required=False, help="Optional - test rail suite case id")
    parser.add_argument("-c", "--confluencefile", type=str, required=False,
                        help="Optional - confluence attachment filename")
    parser.add_argument("-bl", "--browserlocation", type=str, required=False,
                        help="Optional - determine browser location")
    parser.add_argument("-dc", "--desiredcapabilities", type=str, required=False,
                        help="Optional - determine browser desired capabilities")
    parser.add_argument("-z", "--zapenabled", type=str, required=False,
                        help="Optional - determine if zap is enabled")
    parser.add_argument("-ph", "--proxyhost", type=str, required=False,
                        help="Optional - specified proxy host")
    parser.add_argument("-pp", "--proxyport", type=str, required=False,
                        help="Optional - specified proxy port")
    parser.add_argument("-ppa", "--proxypath", type=str, required=False,
                        help="Optional - specified proxy path")
    parser.add_argument("-nl", "--networklogger", type=str, required=False,
                        help="Optional - specified network logger")
    
    args = parser.parse_args()
    print('Execution file = %s' % args.executionfile)
    print('Suites base directory = %s' % args.suitebase)
    print('Output root directory: %s' % args.outputbase)
    print('Max parallel suites: %s' % args.maxsuites)
    if args.tags:
        print('Tags: %s' % args.tags)
    else:
        print('Tags: Robot tag list required')
        sys.exit(1)
    if args.reporttitle:
        print('Custom Report Title: %s' % args.reporttitle)
    else:
        print('Custom Report Title: report title is required')
        sys.exit(1)
    if args.devmode:
        print(f"Dev mode: {args.devmode}")
        if not args.testsuite:
            print("Dev mode: missing test suite name required")
            sys.exit(1)
        if not args.testcases:
            print("Dev mode: missing test case(s) list required")
            sys.exit(1)
        print(f"Test suite: {args.testsuite}")
        print(f"Test Case(s): {args.testcases}")
        print(f"Agency: {args.agency}")
    else:
        args.devmode = 0
        args.testsuite = False
        args.testcases = False
        print("Dev mode: 0 so ignoring any dev mode arguments")

    if not args.reruntests:
        args.reruntests = 0
    print(f"Rerun test: {args.reruntests}")

    tr_enabled = is_true(args.testrailresultenabled)
    args.testrailresultenabled = "TRUE" if tr_enabled else "FALSE"

    if tr_enabled:
        print(f"Test rail result enabled: {args.testrailresultenabled}")
        if not args.civicplatformversion:
            print("Test rail result enabled: missing civic platform version")
            sys.exit(1)

        if args.testrailprojectid and args.testrailsuiteid:
            print(f"Test rail project id {args.testrailprojectid} and Test rail test suite id {args.testrailsuiteid}")
        else:
            v = args.civicplatformversion.lower()
            if ("aca" in v) or ("aca-report" in v) or ("aca-payment" in v) or ("aca-acds" in v):
                args.testrailprojectid = 4
                args.testrailsuiteid = 2379
            elif ("aa" in v) or ("report" in v) or ("payment" in v) or ("acds" in v):
                args.testrailprojectid = 3
                args.testrailsuiteid = 2380
            elif "agis" in v:
                args.testrailprojectid = 101
                args.testrailsuiteid = 2378
            else:
                print("Test rail project/suite not detected from civic platform version; defaulting to AA")
                args.testrailprojectid = 3
                args.testrailsuiteid = 2380

            print(f"Test rail project id {args.testrailprojectid} and Test rail test suite id {args.testrailsuiteid}")
    else:
        args.testrailprojectid = 0
        args.testrailsuiteid = 0
        
    if not args.confluencefile:
        args.confluencefile = False
    if not args.browserlocation:
        args.browserlocation = 'local'
    else:
        print('desired capabilities: %s' % args.desiredcapabilities)
        if args.browserlocation == 'remote':
            if not args.desiredcapabilities:
                args.desiredcapabilities = 'windows.chrome.91'
        else:
                args.browserlocation = 'local'
    print('browser location: %s' % args.browserlocation)
    # check input parameters
    if args.maxsuites < 1:
        print('maxsuites needs to be >1')
        sys.exit(1)
    if not os.path.exists(args.executionfile):
        print('executionfile file not found')
        sys.exit(1)
    if not os.path.isdir(args.suitebase):
        print('suitebase directory not found')
        sys.exit(1)
    if not os.path.isdir(args.outputbase):
        print('outputbase directory not found')
        sys.exit(1)
    if args.zapenabled:
        if args.proxyhost:
            print('proxy host: %s' % args.proxyhost)
        else:
            print('Missing proxy host')
            sys.exit(1)
        if args.proxyport:
            print('proxy port: %s' % args.proxyport)
        else:
            print('Missing proxy port')
            sys.exit(1)
        if args.proxypath:
            print('proxy path: %s' % args.proxypath)
        else:
            print('Missing proxy path')
            sys.exit(1)
    else:
        args.zapenabled = False
        args.proxyport = -1
        args.proxyhost = None
        args.proxypath = None
    if args.networklogger is not None and args.networklogger.upper() == 'TRUE':
        args.networklogger = 'TRUE'
    else:
        args.networklogger = 'FALSE'
    os.environ['NETWORK_LOGGER_ENABLED'] = args.networklogger
    print(f"Network logger enabled: {args.networklogger}")

    # execute
    try:
        runner = ParallelRunner(execution_file=args.executionfile, suite_base_path=args.suitebase,
                                output_base_path=args.outputbase, max_suites=args.maxsuites, robot_tags=args.tags, report_title=args.reporttitle, dev_mode=args.devmode,
                                test_suite_name=args.testsuite, test_case_list=args.testcases, agency=args.agency, civic_platform_version=args.civicplatformversion,
                                test_rail_result_enabled=args.testrailresultenabled, reruntests=args.reruntests, testrail_project_id=args.testrailprojectid,
                                testrail_suite_id=args.testrailsuiteid, confluence_attachment_name=args.confluencefile, browser_location=args.browserlocation,
                                desired_capabilities=args.desiredcapabilities, zap_enabled=args.zapenabled, proxy_host=args.proxyhost, proxy_port=args.proxyport, 
                                proxy_path=args.proxypath, network_logger_enabled=args.networklogger)
        runner.execute_suites()
    except Exception as e:
        print('Error - %s' % str(e))
        sys.exit(1)


if __name__ == "__main__":
    main()
