Chromium Code Reviews| OLD | NEW |
|---|---|
| (Empty) | |
| 1 # Coppyright 2016 The Chromium Authors. All rights reserved. | |
|
qyearsley
2016/07/12 23:00:15
Coppyright -> Copyright
| |
| 2 # Use of this source code is governed by a BSD-style license that can be | |
| 3 # found in the LICENSE file. | |
| 4 | |
| 5 | |
| 6 from webkitpy.common.checkout.scm.git import Git | |
| 7 from webkitpy.common.net import buildbot | |
| 8 from webkitpy.common.net import rietveld | |
| 9 from webkitpy.common.net.web import Web | |
| 10 from webkitpy.layout_tests.builder_list import BuilderList | |
| 11 from webkitpy.common.config.builders import BUILDERS as Builders_list_dict | |
| 12 import logging | |
| 13 | |
| 14 | |
| 15 # This script is designed to output a list of Test Expectations lines to be adde d to TestExpectations.py by | |
| 16 # retrieving the latest try_job results for the current cl issue connected to th e local branch and parsing it | |
| 17 # to develop a dictionary of dictionaries that contain: | |
| 18 # {Test Name: {Platform: {'actual': 'foo', 'expected': 'foo', 'bug':'crbug.com/# ####'}}} | |
|
qyearsley
2016/07/12 23:00:15
Good - module-level descriptions with examples of
| |
| 19 | |
| 20 _log = logging.getLogger(__name__) | |
| 21 | |
| 22 | |
| 23 TRY_BOTS = ['linux_chromium_rel_ng', 'mac_chromium_rel_ng', 'win_chromium_rel_ng '] | |
| 24 | |
| 25 | |
| 26 def main(): | |
| 27 line_expectations_dict = {} | |
| 28 line_list = [] | |
| 29 counter = 0 | |
| 30 web = Web() | |
| 31 try_jobs_info = get_try_jobs_information(web) | |
| 32 while counter < len(TRY_BOTS): | |
| 33 try: | |
| 34 platform_results_dict = get_try_job_results(try_jobs_info, counter) | |
| 35 line_expectations_dict = merge_dicts(line_expectations_dict, platfor m_results_dict) | |
| 36 counter += 1 | |
| 37 except IndexError: | |
| 38 print "no tryjob info was collected" | |
| 39 return 1 | |
| 40 line_expectations_dict = update_platforms(line_expectations_dict) | |
| 41 line_list = create_line_list(line_expectations_dict) | |
| 42 return line_list | |
| 43 | |
| 44 # This function will return only tryjobs with failing results. | |
| 45 # If no failing results, try_job info will not be returned. If one try server | |
| 46 # has two try jobs, it will return both. | |
| 47 | |
| 48 | |
| 49 def get_try_jobs_information(web): | |
| 50 git = Git('.') | |
| 51 issue_number = git.get_issue_number() | |
| 52 info = rietveld.latest_try_jobs(issue_number, TRY_BOTS, web) | |
| 53 return info | |
| 54 | |
| 55 | |
| 56 def _generate_results_dict(layout_test_list): | |
| 57 test_dict = {} | |
| 58 builder_list = BuilderList(Builders_list_dict) | |
| 59 builder_name = layout_test_list.builder_name() | |
| 60 platform = builder_list.port_name_for_builder_name(builder_name) | |
| 61 dash = platform.find("-") | |
| 62 if dash != -1: | |
| 63 platform = platform[dash + 1:].capitalize() | |
| 64 for result in layout_test_list.didnt_run_as_expected_results(): | |
| 65 test_dict[result.test_name()] = {platform: {'expected': result.expected_ results(), 'actual': result.actual_results(), 'bug': 'crbug.com/626703'}} | |
| 66 return test_dict | |
| 67 | |
| 68 | |
| 69 def get_try_job_results(try_jobs_data, index): | |
| 70 builder_name = try_jobs_data[index][0] | |
| 71 build_number = try_jobs_data[index][1] | |
| 72 builder = buildbot.Builder(builder_name, buildbot.BuildBot()) | |
| 73 build = buildbot.Build(builder, build_number) | |
| 74 layout_test_results = builder.fetch_layout_test_results(build.results_url()) | |
| 75 failing_results_dict = _generate_results_dict(layout_test_results) | |
| 76 return failing_results_dict | |
| 77 | |
| 78 | |
| 79 def _remove_duplicates(failing_paths): | |
| 80 seen = set() | |
| 81 new_list = [] | |
| 82 for dictionary in failing_paths: | |
| 83 path = tuple(dictionary.items()) | |
| 84 if path not in seen: | |
| 85 seen.add(path) | |
| 86 new_list.append(dict(path)) | |
| 87 return new_list | |
| 88 | |
| 89 | |
| 90 def merge_dicts(final, temp, path=None): | |
| 91 if path is None: | |
| 92 path = [] | |
| 93 for key in temp: | |
| 94 if key in final: | |
| 95 if (isinstance(final[key], dict)) and isinstance(temp[key], dict): | |
| 96 merge_dicts(final[key], temp[key], path + [str(key)]) | |
| 97 elif final[key] == temp[key]: | |
| 98 pass | |
| 99 else: | |
| 100 raise Exception('conflict at %s' % '.'.join(path)) | |
| 101 else: | |
| 102 final[key] = temp[key] | |
| 103 return final | |
| 104 | |
| 105 # note this function may break if there are more than 3 inner_keys. | |
| 106 # as of right now, the inner_keys should only be [win, linux, mac] | |
| 107 | |
| 108 | |
| 109 def update_platforms(final): | |
| 110 for value in final.values(): | |
| 111 platform = [set()] | |
| 112 inner_keys = value.keys() | |
| 113 tuple_result = {} | |
| 114 for i, item in enumerate(inner_keys): | |
| 115 if (i + 1) < len(inner_keys): | |
| 116 if value[item] == value[inner_keys[i + 1]]: | |
| 117 tuple_result = value[item] | |
| 118 platform[0].add(item) | |
| 119 if (i + 2) == len(inner_keys): | |
| 120 platform[0].add(inner_keys[i + 1]) | |
| 121 elif (i == 0) and (value[item] == value[inner_keys[len(inner_key s) - 1]]): | |
| 122 platform[0].add(item) | |
| 123 platform[0].add(inner_keys[len(inner_keys) - 1]) | |
| 124 if len(platform[0]) == 0: | |
| 125 continue | |
| 126 else: | |
| 127 value[tuple(platform[0])] = tuple_result | |
| 128 for i in platform[0]: | |
| 129 value.pop(i) | |
| 130 return final | |
|
qyearsley
2016/07/12 23:00:15
On first look, I'm having difficulty understanding
| |
| 131 | |
| 132 | |
| 133 def get_expectations(results): | |
| 134 expectations = [] | |
| 135 failure_expectations = ['TEXT', 'FAIL', 'IMAGE+TEXT', 'IMAGE'] | |
| 136 pass_crash_timeout = ['TIMEOUT', 'CRASH', 'PASS'] | |
| 137 if results['expected'] in pass_crash_timeout and results['actual'] in failur e_expectations: | |
| 138 expectations.append('Failure') | |
| 139 if results['expected'] in failure_expectations and results['actual'] in pass _crash_timeout: | |
| 140 expectations.append(results['actual'].capitalize()) | |
| 141 if results['expected'] in pass_crash_timeout and results['actual'] in pass_c rash_timeout: | |
| 142 expectations.append(results['actual'].capitalize()) | |
| 143 expectations.append(results['expected'].capitalize()) | |
| 144 return expectations | |
| 145 | |
| 146 | |
| 147 def create_line_list(dictionary): | |
| 148 line_list = [] | |
| 149 for key, value in dictionary.iteritems(): | |
| 150 test_name = key | |
| 151 for key2 in value: | |
| 152 platform = [] | |
| 153 bug = [] | |
| 154 expectations = [] | |
| 155 if isinstance(key2, tuple): | |
| 156 platform = list(key2) | |
| 157 else: | |
| 158 platform.append(key2) | |
| 159 bug.append(value[key2]['bug']) | |
| 160 expectations = get_expectations(value[key2]) | |
| 161 line = '%s [ %s ] %s [ %s ]' % (bug[0], ' '.join(platform), test_nam e, ' '.join(expectations)) | |
| 162 line_list.append(line) | |
| 163 return line_list | |
| OLD | NEW |