OLD | NEW |
(Empty) | |
| 1 # Copyright (c) 2011 The Chromium OS Authors. All rights reserved. |
| 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 import logging |
| 7 import os |
| 8 import re |
| 9 |
| 10 from autotest_lib.frontend.afe import readonly_connection |
| 11 |
| 12 |
| 13 BUILD_PATTERN = re.compile( |
| 14 '[\w]*\-[\w]*\-r[\w]*\-' |
| 15 '([\d]*\.[\d]*\.[\d]*\.[\d]*)-(r[\w]{8})-(b[\d]*)') |
| 16 |
| 17 |
| 18 def AbbreviateBuild(build): |
| 19 m = re.match(BUILD_PATTERN, build) |
| 20 if not m: |
| 21 logging.warning('Skipping poorly formatted build: %s.', build) |
| 22 return build |
| 23 new_build = '%s-%s' % (m.group(1), m.group(3)) |
| 24 return new_build |
| 25 |
| 26 |
| 27 def AggregateBuilds(test_key, data_list): |
| 28 build_dict = {} |
| 29 build_order = [] |
| 30 job_tags = [] |
| 31 for build, tag, value in data_list: |
| 32 build = AbbreviateBuild(build) |
| 33 if not build in build_dict: |
| 34 build_order.append(build) |
| 35 job_tags.append(tag) |
| 36 build_dict.setdefault(build, []).append(value) |
| 37 gviz_build_data = [] |
| 38 for build in build_order: |
| 39 value_list = build_dict[build] |
| 40 gviz_build_data.append({ |
| 41 'build': build, |
| 42 test_key: round(sum(value_list, 0.0) / len(value_list), 2)}) |
| 43 return gviz_build_data, job_tags |
| 44 |
| 45 |
| 46 def GetChartData(boards, netbook, from_build, to_build, |
| 47 test_name, test_key, interval): |
| 48 cursor = readonly_connection.connection().cursor() |
| 49 |
| 50 # Common query template that gets re-used. |
| 51 platform = 'netbook_%s' % netbook |
| 52 common_query = [ |
| 53 "SELECT %s", |
| 54 "FROM tko_perf_view_2", |
| 55 "WHERE job_name REGEXP %s", |
| 56 " AND platform = '%s'" % platform, |
| 57 " AND test_name = '%s'" % test_name, |
| 58 " AND iteration_key = '%s'" % test_key, |
| 59 " AND job_owner = 'chromeos-test'", |
| 60 " AND NOT ISNULL(iteration_value)", |
| 61 " AND iteration_value >= 0.0", |
| 62 " AND NOT ISNULL(test_started_time)", |
| 63 " AND NOT ISNULL(test_finished_time)", |
| 64 " AND NOT ISNULL(job_finished_time)"] |
| 65 common_job_name = "'(%s).*'" |
| 66 |
| 67 # Query notes: |
| 68 # 1. Getting the job_name to be able to aggregate different jobs that run |
| 69 # the same test on the same build. |
| 70 # 2. Getting every data point to be able to discard outliers. |
| 71 # 3. Default order of date. |
| 72 # 4. Uses subqueries to find bracketing dates mapping version to job_names. |
| 73 if from_build: |
| 74 job_name = common_job_name % '|'.join( |
| 75 '%s-%s' % (b, from_build.replace('.', '\.')) for b in boards.split('&')) |
| 76 min_query = ' '.join(common_query) % ( |
| 77 'IFNULL(MIN(test_started_time), DATE_SUB(NOW(), INTERVAL 1 DAY))', |
| 78 job_name) |
| 79 else: |
| 80 if not interval: |
| 81 interval = '2 WEEK' |
| 82 min_query = 'SELECT DATE_SUB(NOW(), INTERVAL %s)' % interval |
| 83 |
| 84 if to_build: |
| 85 job_name = common_job_name % '|'.join( |
| 86 '%s-%s' % (b, to_build.replace('.', '\.')) for b in boards.split('&')) |
| 87 max_query = ' '.join(common_query) % ( |
| 88 'IFNULL(MAX(test_started_time), NOW())', job_name) |
| 89 else: |
| 90 max_query = 'SELECT NOW()' |
| 91 |
| 92 iteration_values = 'job_name, job_tag, iteration_value' |
| 93 job_name = common_job_name % '|'.join(boards.split('&')) |
| 94 query = [ |
| 95 ' '.join(common_query) % (iteration_values, job_name), |
| 96 ' AND test_started_time > (%s)' % min_query, |
| 97 ' AND test_finished_time < (%s)' % max_query, |
| 98 'ORDER BY test_started_time'] |
| 99 cursor.execute(' '.join(query)) |
| 100 return AggregateBuilds(test_key, cursor.fetchall()) |
OLD | NEW |