1# Copyright 2017 The Chromium 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 5import logging 6import os 7import socket 8import time 9 10from autotest_lib.client.common_lib import base_utils 11from autotest_lib.client.common_lib import global_config 12from autotest_lib.client.common_lib import time_utils 13from autotest_lib.site_utils import job_directories 14 15CONFIG=global_config.global_config 16 17RETRIEVE_LOGS_CGI = CONFIG.get_config_value( 18 'BUG_REPORTING', 'retrieve_logs_cgi', default='') 19USE_PROD_SERVER = CONFIG.get_config_value( 20 'SERVER', 'use_prod_sponge_server', default=False, type=bool) 21 22 23class AutotestJobInfo(object): 24 """Autotest job info.""" 25 26 # Tell the uploader what type of info this object holds. 27 tags=['autotest'] 28 29 # Version of the data stored. 30 version = 2 31 32 def __init__(self, job): 33 self._job = job 34 self._tasks = list( 35 self.create_task_info(test) for test in self._job.tests) 36 37 self.build = job.build 38 self.build_version = job.build_version 39 self.board = job.board 40 41 @property 42 def id(self): 43 """The id of the autotest job.""" 44 return job_directories.get_job_id_or_task_id(self._job.dir) 45 46 @property 47 def label(self): 48 """The label of the autotest job.""" 49 return self._job.label 50 51 @property 52 def user(self): 53 """The user who launched the autotest job.""" 54 return self._job.user 55 56 @property 57 def start_time(self): 58 """The utc start time of the autotest job.""" 59 return self._job.keyval_dict.get('job_started', time.time()) 60 61 @property 62 def end_time(self): 63 """The utc end time of the autotest job.""" 64 return self._job.keyval_dict.get('job_finished', time.time()) 65 66 @property 67 def dut(self): 68 """The dut for the job.""" 69 return self._job.machine 70 71 @property 72 def drone(self): 73 """The drone used to run the job.""" 74 return self._job.keyval_dict.get('drone', socket.gethostname()) 75 76 @property 77 def keyvals(self): 78 """Keyval dict for this job.""" 79 return self._job.keyval_dict 80 81 @property 82 def tasks(self): 83 """All tests that this job ran.""" 84 return self._tasks 85 86 @property 87 def results_dir(self): 88 """The directory where job results are stored.""" 89 return os.path.abspath(self._job.dir) 90 91 @property 92 def results_url(self): 93 """The url where results are stored.""" 94 return '%s/results/%s-%s/%s' % ( 95 RETRIEVE_LOGS_CGI, self.id, self.user, self.dut) 96 97 @property 98 def is_official(self): 99 """If this is a production result.""" 100 return USE_PROD_SERVER 101 102 def create_task_info(self, test): 103 """Thunk for creating task info. 104 105 @param test: The autotest test. 106 107 @returns The task info. 108 """ 109 logging.info('Using default autotest task info for %s.', test.testname) 110 return AutotestTaskInfo(test, self) 111 112 113class AutotestTaskInfo(object): 114 """Info about an autotest test.""" 115 116 # Tell the uploader what type of info is kept in this task. 117 tags = ['autotest'] 118 119 # A list of logs to upload for this task. 120 logs = ['debug', 'status.log', 'crash', 'keyval', 'control', 'control.srv'] 121 122 # Version of the data stored. 123 version = 2 124 125 def __init__(self, test, job): 126 """ 127 @param test: The autotest test to create this task from. 128 @param job: The job info that owns this task. 129 """ 130 self._test = test 131 self._job = job 132 133 keyvals_file = os.path.join(self.results_dir, 'keyval') 134 self.keyvals = base_utils.read_keyval(keyvals_file) 135 136 @property 137 def taskname(self): 138 """The name of the test.""" 139 return self._test.testname 140 141 @property 142 def status(self): 143 """The autotest status of this test.""" 144 return self._test.status 145 146 @property 147 def start_time(self): 148 """The utc recorded time of when this test started.""" 149 return time_utils.to_utc_timestamp(self._test.started_time) 150 151 @property 152 def end_time(self): 153 """The utc recorded time of when this test ended.""" 154 return time_utils.to_utc_timestamp(self._test.finished_time) 155 156 @property 157 def subdir(self): 158 """The sub directory used for this test.""" 159 return self._test.subdir 160 161 @property 162 def attributes(self): 163 """Attributes of this task.""" 164 return getattr(self._test, 'attributes', {}) 165 166 @property 167 def reason(self): 168 """The reason for this tasks status.""" 169 return getattr(self._test, 'reason', None) 170 171 @property 172 def results_dir(self): 173 """The full directory where results are stored for this test.""" 174 if self.subdir == '----' or not self.subdir: 175 return self._job.results_dir 176 else: 177 return os.path.join(self._job.results_dir, self.subdir) 178 179 @property 180 def is_test(self): 181 """True if this task is an actual test that ran.""" 182 return self.subdir != '----' 183