|
| 1 | +import humanize |
| 2 | +import rich.box |
| 3 | +from rich.panel import Panel |
| 4 | +from rich.table import Table |
| 5 | +from rich.console import ( |
| 6 | + Group, |
| 7 | + RenderableType, |
| 8 | +) |
| 9 | +from rich.text import Text |
| 10 | + |
| 11 | +from .. import ( |
| 12 | + config, |
| 13 | + models, |
| 14 | +) |
| 15 | + |
| 16 | + |
| 17 | +def to_console( |
| 18 | + parsed_result: models.TestSuiteResult, |
| 19 | + serialization_details: models.SerializationDetails, |
| 20 | + context: config.CiteRunnerContext, |
| 21 | +) -> Group: |
| 22 | + overview_message = Text( |
| 23 | + f"Test suite has {'passed 🏅' if parsed_result.passed else 'failed ❌'}" |
| 24 | + f"\n\n" |
| 25 | + f"- Ran {parsed_result.num_tests_total} tests in " |
| 26 | + f"{humanize.precisedelta(parsed_result.test_run_duration)}\n" |
| 27 | + f"- 🔴 Failed {parsed_result.num_failed_tests} tests\n" |
| 28 | + f"- 🟡 Skipped {parsed_result.num_skipped_tests} tests\n" |
| 29 | + f"- 🟢 Passed {parsed_result.num_passed_tests} tests\n" |
| 30 | + ) |
| 31 | + contents = [overview_message] |
| 32 | + if serialization_details.include_summary: |
| 33 | + summary_table = Table(title="Conformance classes", expand=True) |
| 34 | + summary_table.add_column("Class") |
| 35 | + summary_table.add_column("🔴 Failed") |
| 36 | + summary_table.add_column("🟡 Skipped") |
| 37 | + summary_table.add_column("🟢 Passed") |
| 38 | + for conf_class in parsed_result.conformance_class_results: |
| 39 | + summary_table.add_row( |
| 40 | + conf_class.title, |
| 41 | + str(conf_class.num_failed_tests), |
| 42 | + str(conf_class.num_skipped_tests), |
| 43 | + str(conf_class.num_passed_tests), |
| 44 | + ) |
| 45 | + summary_contents = Panel(summary_table, box=rich.box.SIMPLE) |
| 46 | + contents.append(summary_contents) |
| 47 | + if ( |
| 48 | + serialization_details.include_failed_detail |
| 49 | + and parsed_result.num_failed_tests > 0 |
| 50 | + ): |
| 51 | + failed_contents = _render_detail_section( |
| 52 | + parsed_result, models.TestStatus.FAILED |
| 53 | + ) |
| 54 | + contents.append(failed_contents) |
| 55 | + if ( |
| 56 | + serialization_details.include_skipped_detail |
| 57 | + and parsed_result.num_skipped_tests > 0 |
| 58 | + ): |
| 59 | + skipped_contents = _render_detail_section( |
| 60 | + parsed_result, models.TestStatus.SKIPPED |
| 61 | + ) |
| 62 | + contents.append(skipped_contents) |
| 63 | + if ( |
| 64 | + serialization_details.include_passed_detail |
| 65 | + and parsed_result.num_passed_tests > 0 |
| 66 | + ): |
| 67 | + passed_contents = _render_detail_section( |
| 68 | + parsed_result, models.TestStatus.PASSED |
| 69 | + ) |
| 70 | + contents.append(passed_contents) |
| 71 | + panel_group = Group( |
| 72 | + Panel(Group(*contents), title=f"Test suite {parsed_result.suite_title}"), |
| 73 | + ) |
| 74 | + return panel_group |
| 75 | + |
| 76 | + |
| 77 | +def _render_detail_section( |
| 78 | + parsed_result: models.TestSuiteResult, |
| 79 | + detail_type: models.TestStatus, |
| 80 | +) -> RenderableType: |
| 81 | + conf_classes_contents = [] |
| 82 | + title = { |
| 83 | + models.TestStatus.PASSED: "🟢 Passed tests", |
| 84 | + models.TestStatus.FAILED: "🔴 Failed tests", |
| 85 | + models.TestStatus.SKIPPED: "🟡 Skipped tests", |
| 86 | + }[detail_type] |
| 87 | + for conf_class in parsed_result.conformance_class_results: |
| 88 | + comparator, outcome_color, test_case_result_generator = { |
| 89 | + models.TestStatus.PASSED: ( |
| 90 | + conf_class.num_passed_tests, |
| 91 | + "green", |
| 92 | + conf_class.gen_passed_tests, |
| 93 | + ), |
| 94 | + models.TestStatus.FAILED: ( |
| 95 | + conf_class.num_failed_tests, |
| 96 | + "red", |
| 97 | + conf_class.gen_failed_tests, |
| 98 | + ), |
| 99 | + models.TestStatus.SKIPPED: ( |
| 100 | + conf_class.num_skipped_tests, |
| 101 | + "bright_yellow", |
| 102 | + conf_class.gen_skipped_tests, |
| 103 | + ), |
| 104 | + }[detail_type] |
| 105 | + if comparator > 0: |
| 106 | + test_case_group_content = [] |
| 107 | + for test_case_result in test_case_result_generator(): |
| 108 | + test_case_group_content.append( |
| 109 | + Panel( |
| 110 | + Group( |
| 111 | + Text.assemble( |
| 112 | + ("Test case: ", "yellow"), test_case_result.identifier |
| 113 | + ), |
| 114 | + Text.assemble( |
| 115 | + ("Outcome: ", "yellow"), |
| 116 | + (test_case_result.status.value, outcome_color), |
| 117 | + ), |
| 118 | + Text.assemble( |
| 119 | + ("Description: ", "yellow"), |
| 120 | + test_case_result.description or "", |
| 121 | + ), |
| 122 | + Text.assemble( |
| 123 | + ("Detail: ", "yellow"), test_case_result.detail or "" |
| 124 | + ), |
| 125 | + ), |
| 126 | + box=rich.box.SIMPLE, |
| 127 | + title_align="left", |
| 128 | + ), |
| 129 | + ) |
| 130 | + conf_classes_contents.append( |
| 131 | + Panel( |
| 132 | + Group(*test_case_group_content), |
| 133 | + title=conf_class.title, |
| 134 | + title_align="left", |
| 135 | + ) |
| 136 | + ) |
| 137 | + failed_contents = Panel( |
| 138 | + Group(*conf_classes_contents), |
| 139 | + title=title, |
| 140 | + title_align="left", |
| 141 | + box=rich.box.SIMPLE, |
| 142 | + ) |
| 143 | + return failed_contents |
0 commit comments