Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(389)

Side by Side Diff: build/android/test_runner.py

Issue 2933993002: Add local results details pages.
Patch Set: Add --local-output arg which enables local results detail pages. Created 3 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 #!/usr/bin/env python 1 #!/usr/bin/env python
2 # 2 #
3 # Copyright 2013 The Chromium Authors. All rights reserved. 3 # Copyright 2013 The Chromium Authors. All rights reserved.
4 # Use of this source code is governed by a BSD-style license that can be 4 # Use of this source code is governed by a BSD-style license that can be
5 # found in the LICENSE file. 5 # found in the LICENSE file.
6 6
7 """Runs all types of tests from one unified interface.""" 7 """Runs all types of tests from one unified interface."""
8 8
9 import argparse 9 import argparse
10 import collections 10 import collections
11 import contextlib 11 import contextlib
12 import itertools 12 import itertools
13 import logging 13 import logging
14 import os 14 import os
15 import shutil 15 import shutil
16 import signal 16 import signal
17 import sys 17 import sys
18 import tempfile
18 import threading 19 import threading
19 import traceback 20 import traceback
20 import unittest 21 import unittest
21 22
22 # Import _strptime before threaded code. datetime.datetime.strptime is 23 # Import _strptime before threaded code. datetime.datetime.strptime is
23 # threadsafe except for the initial import of the _strptime module. 24 # threadsafe except for the initial import of the _strptime module.
24 # See http://crbug.com/724524 and https://bugs.python.org/issue7980. 25 # See http://crbug.com/724524 and https://bugs.python.org/issue7980.
25 import _strptime # pylint: disable=unused-import 26 import _strptime # pylint: disable=unused-import
26 27
27 from pylib.constants import host_paths 28 from pylib.constants import host_paths
28 29
29 if host_paths.DEVIL_PATH not in sys.path: 30 if host_paths.DEVIL_PATH not in sys.path:
30 sys.path.append(host_paths.DEVIL_PATH) 31 sys.path.append(host_paths.DEVIL_PATH)
31 32
32 from devil import base_error 33 from devil import base_error
33 from devil.utils import reraiser_thread 34 from devil.utils import reraiser_thread
34 from devil.utils import run_tests_helper 35 from devil.utils import run_tests_helper
35 36
36 from pylib import constants 37 from pylib import constants
37 from pylib.base import base_test_result 38 from pylib.base import base_test_result
38 from pylib.base import environment_factory 39 from pylib.base import environment_factory
39 from pylib.base import test_instance_factory 40 from pylib.base import test_instance_factory
40 from pylib.base import test_run_factory 41 from pylib.base import test_run_factory
41 from pylib.results import json_results 42 from pylib.results import json_results
42 from pylib.results import report_results 43 from pylib.results import report_results
44 from pylib.results.presentation import test_results_presentation
43 from pylib.utils import logdog_helper 45 from pylib.utils import logdog_helper
44 from pylib.utils import logging_utils 46 from pylib.utils import logging_utils
47 from pylib.utils import test_output_saver_factory
45 48
46 from py_utils import contextlib_ext 49 from py_utils import contextlib_ext
47 50
48 51
49 _DEVIL_STATIC_CONFIG_FILE = os.path.abspath(os.path.join( 52 _DEVIL_STATIC_CONFIG_FILE = os.path.abspath(os.path.join(
50 host_paths.DIR_SOURCE_ROOT, 'build', 'android', 'devil_config.json')) 53 host_paths.DIR_SOURCE_ROOT, 'build', 'android', 'devil_config.json'))
51 54
52 55
53 def AddTestLauncherOptions(parser): 56 def AddTestLauncherOptions(parser):
54 """Adds arguments mirroring //base/test/launcher. 57 """Adds arguments mirroring //base/test/launcher.
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after
134 help='Run the test scripts in platform mode, which ' 137 help='Run the test scripts in platform mode, which '
135 'conceptually separates the test runner from the ' 138 'conceptually separates the test runner from the '
136 '"device" (local or remote, real or emulated) on ' 139 '"device" (local or remote, real or emulated) on '
137 'which the tests are running. [experimental]') 140 'which the tests are running. [experimental]')
138 141
139 parser.add_argument( 142 parser.add_argument(
140 '-e', '--environment', 143 '-e', '--environment',
141 default='local', choices=constants.VALID_ENVIRONMENTS, 144 default='local', choices=constants.VALID_ENVIRONMENTS,
142 help='Test environment to run in (default: %(default)s).') 145 help='Test environment to run in (default: %(default)s).')
143 146
147 parser.add_argument(
148 '--local-output', action='store_true',
149 help='Whether to archive test output locally and generate '
150 'a local results detail page.')
151
144 class FastLocalDevAction(argparse.Action): 152 class FastLocalDevAction(argparse.Action):
145 def __call__(self, parser, namespace, values, option_string=None): 153 def __call__(self, parser, namespace, values, option_string=None):
146 namespace.verbose_count = max(namespace.verbose_count, 1) 154 namespace.verbose_count = max(namespace.verbose_count, 1)
147 namespace.num_retries = 0 155 namespace.num_retries = 0
148 namespace.enable_device_cache = True 156 namespace.enable_device_cache = True
149 namespace.enable_concurrent_adb = True 157 namespace.enable_concurrent_adb = True
150 namespace.skip_clear_data = True 158 namespace.skip_clear_data = True
151 namespace.extract_test_list_from_filter = True 159 namespace.extract_test_list_from_filter = True
152 160
153 parser.add_argument( 161 parser.add_argument(
(...skipping 624 matching lines...) Expand 10 before | Expand all | Expand 10 after
778 logging.critical( 786 logging.critical(
779 'Logcat: %s', logdog_helper.get_viewer_url('unified_logcats')) 787 'Logcat: %s', logdog_helper.get_viewer_url('unified_logcats'))
780 788
781 789
782 logcats_uploader = contextlib_ext.Optional( 790 logcats_uploader = contextlib_ext.Optional(
783 upload_logcats_file(), 791 upload_logcats_file(),
784 'upload_logcats_file' in args and args.upload_logcats_file) 792 'upload_logcats_file' in args and args.upload_logcats_file)
785 793
786 ### Set up test objects. 794 ### Set up test objects.
787 795
796 test_output_saver = test_output_saver_factory.CreateTestOutputSaver(args)
788 env = environment_factory.CreateEnvironment(args, infra_error) 797 env = environment_factory.CreateEnvironment(args, infra_error)
789 test_instance = test_instance_factory.CreateTestInstance(args, infra_error) 798 test_instance = test_instance_factory.CreateTestInstance(args, infra_error)
790 test_run = test_run_factory.CreateTestRun( 799 test_run = test_run_factory.CreateTestRun(
791 args, env, test_instance, infra_error) 800 args, env, test_instance, test_output_saver, infra_error)
792 801
793 ### Run. 802 ### Run.
794 803
795 with json_writer, logcats_uploader, env, test_instance, test_run: 804 with json_writer, logcats_uploader, env, test_instance, test_run:
796 805
797 repetitions = (xrange(args.repeat + 1) if args.repeat >= 0 806 repetitions = (xrange(args.repeat + 1) if args.repeat >= 0
798 else itertools.count()) 807 else itertools.count())
799 result_counts = collections.defaultdict( 808 result_counts = collections.defaultdict(
800 lambda: collections.defaultdict(int)) 809 lambda: collections.defaultdict(int))
801 iteration_count = 0 810 iteration_count = 0
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
845 all_pass += 1 854 all_pass += 1
846 855
847 logging.critical('%s of %s tests passed in all %s runs', 856 logging.critical('%s of %s tests passed in all %s runs',
848 str(all_pass), 857 str(all_pass),
849 str(tot_tests), 858 str(tot_tests),
850 str(iteration_count)) 859 str(iteration_count))
851 860
852 if args.command == 'perf' and (args.steps or args.single_step): 861 if args.command == 'perf' and (args.steps or args.single_step):
853 return 0 862 return 0
854 863
864 if args.local_output:
jbudorick 2017/06/20 14:12:55 We won't write local output on exception w/ this.
mikecase (-- gone --) 2017/07/10 17:11:11 Like, if the test_runner itself throws an exceptio
865 result_html_string = test_results_presentation.result_details(
866 json_path=args.json_results_file,
867 test_name=args.command,
868 cs_base_url='http://cs.chromium.org',
869 local_output=True)
870 with tempfile.NamedTemporaryFile() as html_tmp:
871 html_tmp.write(result_html_string)
872 html_tmp.flush()
873 link = test_output_saver.Save(
874 html_tmp.name,
875 'test_results_presentation.html',
876 'test_results_presentation',
877 test_output_saver_factory.Datatype.HTML)
878 logging.critical('TEST RESULTS: %s', link)
879
855 return (0 if all(r.DidRunPass() for r in all_iteration_results) 880 return (0 if all(r.DidRunPass() for r in all_iteration_results)
856 else constants.ERROR_EXIT_CODE) 881 else constants.ERROR_EXIT_CODE)
857 882
858 883
859 def DumpThreadStacks(_signal, _frame): 884 def DumpThreadStacks(_signal, _frame):
860 for thread in threading.enumerate(): 885 for thread in threading.enumerate():
861 reraiser_thread.LogThreadStack(thread) 886 reraiser_thread.LogThreadStack(thread)
862 887
863 888
864 def main(): 889 def main():
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after
934 if e.is_infra_error: 959 if e.is_infra_error:
935 return constants.INFRA_EXIT_CODE 960 return constants.INFRA_EXIT_CODE
936 return constants.ERROR_EXIT_CODE 961 return constants.ERROR_EXIT_CODE
937 except: # pylint: disable=W0702 962 except: # pylint: disable=W0702
938 logging.exception('Unrecognized error occurred.') 963 logging.exception('Unrecognized error occurred.')
939 return constants.ERROR_EXIT_CODE 964 return constants.ERROR_EXIT_CODE
940 965
941 966
942 if __name__ == '__main__': 967 if __name__ == '__main__':
943 sys.exit(main()) 968 sys.exit(main())
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698