def _make_names(name): """Takes a name from piglit (using grouptools.SEPARATOR and returns a split classnam, testname pair in junit format. """ classname, testname = grouptools.splitname(name) classname = classname.split(grouptools.SEPARATOR) classname = [junit_escape(e) for e in classname] classname = '.'.join(classname) # Add the test to the piglit group rather than directly to the root # group, this allows piglit junit to be used in conjunction with other # piglit # TODO: It would be nice if other suites integrating with piglit could # set different root names. classname = 'piglit.' + classname return (classname, junit_escape(testname))
def get_result(self, key): """Get the result of a test or subtest. If neither a test nor a subtest instance exist, then raise the original KeyError generated from looking up <key> in the tests attribute. It is the job of the caller to handle this error. Arguments: key -- the key name of the test to return """ try: return self.tests[key].result except KeyError as e: name, test = grouptools.splitname(key) try: return self.tests[name].subtests[test] except KeyError: raise e
def get_result(self, name): """Get all results for a single test. Replace any missing vaules with status.NOTRUN, correclty handles subtests. """ results = [] for res in self.results: try: results.append(res.tests[name].result) except KeyError: results.append(so.NOTRUN) if all(x == so.NOTRUN for x in results): # this is likely a subtest, see if that's the case name, test = grouptools.splitname(name) results = [] for res in self.results: try: results.append(res.tests[name].subtests[test]) except KeyError: results.append(so.NOTRUN) return results
def test_basic(self): assert grouptools.splitname(grouptools.join('g1', 'g2', 't1')) == \ (grouptools.join('g1', 'g2'), 't1')
def _write(self, f, name, data): def calculate_result(): """Set the result.""" expected_result = "pass" # replace special characters and make case insensitive lname = (classname + "." + testname).lower() lname = lname.replace("=", ".") lname = lname.replace(":", ".") if lname in self._expected_failures: expected_result = "failure" # a test can either fail or crash, but not both assert lname not in self._expected_crashes if lname in self._expected_crashes: expected_result = "error" res = None # Add relevant result value, if the result is pass then it doesn't # need one of these statuses if data.result == 'skip': res = etree.SubElement(element, 'skipped') elif data.result in ['fail', 'dmesg-warn', 'dmesg-fail']: if expected_result == "failure": err.text += "\n\nWARN: passing test as an expected failure" res = etree.SubElement(element, 'skipped', message='expected failure') else: res = etree.SubElement(element, 'failure') elif data.result in ['crash', 'timeout']: if expected_result == "error": err.text += "\n\nWARN: passing test as an expected crash" res = etree.SubElement(element, 'skipped', message='expected crash') else: res = etree.SubElement(element, 'error') elif expected_result != "pass": err.text += "\n\nERROR: This test passed when it "\ "expected {0}".format(expected_result) res = etree.SubElement(element, 'failure') # Add the piglit type to the failure result if res is not None: res.attrib['type'] = str(data.result) # Split the name of the test and the group (what junit refers to as # classname), and replace piglits '/' separated groups with '.', after # replacing any '.' with '_' (so we don't get false groups). classname, testname = grouptools.splitname(name) classname = classname.split(grouptools.SEPARATOR) classname = [junit_escape(e) for e in classname] classname = '.'.join(classname) # Add the test to the piglit group rather than directly to the root # group, this allows piglit junit to be used in conjunction with other # piglit # TODO: It would be nice if other suites integrating with piglit could # set different root names. classname = 'piglit.' + classname # Jenkins will display special pages when the test has certain names. # https://jenkins-ci.org/issue/18062 # https://jenkins-ci.org/issue/19810 # The testname variable is used in the calculate_result # closure, and must not have the suffix appended. full_test_name = testname + self._test_suffix if full_test_name in _JUNIT_SPECIAL_NAMES: testname += '_' full_test_name = testname + self._test_suffix # Create the root element element = etree.Element('testcase', name=full_test_name, classname=classname, # Incomplete will not have a time. time=str(data.time.total), status=str(data.result)) # If this is an incomplete status then none of these values will be # available, nor if data.result != 'incomplete': # Add stdout out = etree.SubElement(element, 'system-out') out.text = data.out # Prepend command line to stdout out.text = data.command + '\n' + out.text # Add stderr err = etree.SubElement(element, 'system-err') err.text = data.err err.text += '\n\npid: {}\nstart time: {}\nend time: {}\n'.format( data.pid, data.time.start, data.time.end) calculate_result() else: etree.SubElement(element, 'failure', message='Incomplete run.') f.write(six.text_type(etree.tostring(element).decode('utf-8')))
def write_test(self, name, data): def calculate_result(): """Set the result.""" expected_result = "pass" # replace special characters and make case insensitive lname = (classname + "." + testname).lower() lname = lname.replace("=", ".") lname = lname.replace(":", ".") if lname in self._expected_failures: expected_result = "failure" # a test can either fail or crash, but not both assert lname not in self._expected_crashes if lname in self._expected_crashes: expected_result = "error" res = None # Add relevant result value, if the result is pass then it doesn't # need one of these statuses if data['result'] == 'skip': res = etree.SubElement(element, 'skipped') elif data['result'] in ['warn', 'fail', 'dmesg-warn', 'dmesg-fail']: if expected_result == "failure": err.text += "\n\nWARN: passing test as an expected failure" res = etree.SubElement(element, 'skipped', message='expected failure') else: res = etree.SubElement(element, 'failure') elif data['result'] == 'crash': if expected_result == "error": err.text += "\n\nWARN: passing test as an expected crash" res = etree.SubElement(element, 'skipped', message='expected crash') else: res = etree.SubElement(element, 'error') elif expected_result != "pass": err.text += "\n\nERROR: This test passed when it "\ "expected {0}".format(expected_result) res = etree.SubElement(element, 'failure') # Add the piglit type to the failure result if res is not None: res.attrib['type'] = str(data['result']) # Split the name of the test and the group (what junit refers to as # classname), and replace piglits '/' separated groups with '.', after # replacing any '.' with '_' (so we don't get false groups). classname, testname = grouptools.splitname(name) classname = classname.replace('.', '_') classname = classname.replace(grouptools.SEPARATOR, '.') # Add the test to the piglit group rather than directly to the root # group, this allows piglit junit to be used in conjunction with other # piglit # TODO: It would be nice if other suites integrating with piglit could # set different root names. classname = 'piglit.' + classname # Jenkins will display special pages when the test has certain names. # https://jenkins-ci.org/issue/18062 # https://jenkins-ci.org/issue/19810 # The testname variable is used in the calculate_result # closure, and must not have the suffix appended. full_test_name = testname + self._test_suffix if full_test_name in ('api', 'search'): testname += '_' full_test_name = testname + self._test_suffix # Create the root element element = etree.Element('testcase', name=full_test_name, classname=classname, time=str(data['time']), status=str(data['result'])) # Add stdout out = etree.SubElement(element, 'system-out') out.text = data['out'] # Prepend command line to stdout out.text = data['command'] + '\n' + out.text # Add stderr err = etree.SubElement(element, 'system-err') err.text = data['err'] calculate_result() t = os.path.join(self._dest, 'tests', '{}.xml'.format(self._counter.next())) with open(t, 'w') as f: f.write(etree.tostring(element)) self._fsync(f)