1#!/usr/bin/python2
2"""Create new scenario test instance from an existing results directory.
3
4This automates creation of regression tests for the results parsers.
5There are 2 primary use cases for this.
6
71) Bug fixing: Parser broke on some input in the field and we want
8to start with a test that operates on that input and fails. We
9then apply fixes to the parser implementation until it passes.
10
112) Regression alarms: We take input from various real scenarios that
12work as expected with the parser. These will be used to ensure
13we do not break the expected functionality of the parser while
14refactoring it.
15
16While much is done automatically, a scenario harness is meant to
17be easily extended and configured once generated.
18"""
19
20import optparse, os, shutil, sys
21from os import path
22
23import common
24from autotest_lib.tko.parsers.test import scenario_base
25from autotest_lib.client.common_lib import autotemp
26
27usage = 'usage: %prog [options] results_dirpath scenerios_dirpath'
28parser = optparse.OptionParser(usage=usage)
29parser.add_option(
30    '-n', '--name',
31    help='Name for new scenario instance. Will use dirname if not specified')
32parser.add_option(
33    '-p', '--parser_result_tag',
34    default='v1',
35    help='Storage tag to use for initial parser result.')
36parser.add_option(
37    '-t', '--template_type',
38    default='base',
39    help='Type of unittest module to copy into new scenario.')
40
41
42def main():
43    (options, args) = parser.parse_args()
44    if len(args) < 2:
45        parser.print_help()
46        sys.exit(1)
47
48    results_dirpath = path.normpath(args[0])
49    if not path.exists(results_dirpath) or not path.isdir(results_dirpath):
50        print 'Invalid results_dirpath:', results_dirpath
51        parser.print_help()
52        sys.exit(1)
53
54    scenarios_dirpath = path.normpath(args[1])
55    if not path.exists(scenarios_dirpath) or not path.isdir(scenarios_dirpath):
56        print 'Invalid scenarios_dirpath:', scenarios_dirpath
57        parser.print_help()
58        sys.exit(1)
59
60    results_dirname = path.basename(results_dirpath)
61    # Not everything is a valid python package name, fix if necessary
62    package_dirname = scenario_base.fix_package_dirname(
63        options.name or results_dirname)
64
65    scenario_package_dirpath = path.join(
66        scenarios_dirpath, package_dirname)
67    if path.exists(scenario_package_dirpath):
68        print (
69            'Scenario package already exists at path: %s' %
70            scenario_package_dirpath)
71        parser.print_help()
72        sys.exit(1)
73
74    # Create new scenario package
75    os.mkdir(scenario_package_dirpath)
76
77    # Create tmp_dir
78    tmp_dirpath = autotemp.tempdir(unique_id='new_scenario')
79    copied_dirpath = path.join(tmp_dirpath.name, results_dirname)
80    # Copy results_dir
81    shutil.copytree(results_dirpath, copied_dirpath)
82
83    # scenario_base.sanitize_results_data(copied_dirpath)
84
85    # Launch parser on copied_dirpath, collect emitted test objects.
86    harness = scenario_base.new_parser_harness(copied_dirpath)
87    try:
88        parser_result = harness.execute()
89    except Exception, e:
90        parser_result = e
91
92    scenario_base.store_parser_result(
93        scenario_package_dirpath, parser_result,
94        options.parser_result_tag)
95
96    scenario_base.store_results_dir(
97        scenario_package_dirpath, copied_dirpath)
98
99    scenario_base.write_config(
100        scenario_package_dirpath,
101        status_version=harness.status_version,
102        parser_result_tag=options.parser_result_tag,
103        )
104
105    scenario_base.install_unittest_module(
106        scenario_package_dirpath, options.template_type)
107    tmp_dirpath.clean()
108
109
110if __name__ == '__main__':
111    main()
112