diff --git a/docs/results.md b/docs/results.md index 6c6420b..5485f09 100644 --- a/docs/results.md +++ b/docs/results.md @@ -68,6 +68,16 @@ Example: kci-dev results test --id 'maestro:67d3e293f378f0c5986d3309' --download-logs --json ``` +### build + +Displays all the information from a single build. + +Example: + +```sh +kci-dev results build --id 'maestro:67d409f9f378f0c5986dc7df' --download-logs --json +``` + ## Common parameters ### --origin diff --git a/kcidev/libs/dashboard.py b/kcidev/libs/dashboard.py index b8ef91c..60f2c08 100644 --- a/kcidev/libs/dashboard.py +++ b/kcidev/libs/dashboard.py @@ -99,6 +99,11 @@ def dashboard_fetch_test(test_id, use_json): return dashboard_api_fetch(endpoint, {}, use_json) +def dashboard_fetch_build(build_id, use_json): + endpoint = f"build/{build_id}" + return dashboard_api_fetch(endpoint, {}, use_json) + + def dashboard_fetch_tree_list(origin, use_json): params = { "origin": origin, diff --git a/kcidev/subcommands/results/__init__.py b/kcidev/subcommands/results/__init__.py index 6ceae4c..06b7671 100644 --- a/kcidev/subcommands/results/__init__.py +++ b/kcidev/subcommands/results/__init__.py @@ -5,6 +5,7 @@ import click from libs.dashboard import ( dashboard_fetch_boots, + dashboard_fetch_build, dashboard_fetch_builds, dashboard_fetch_summary, dashboard_fetch_test, @@ -14,6 +15,7 @@ from subcommands.results.parser import ( cmd_builds, cmd_list_trees, + cmd_single_build, cmd_single_test, cmd_summary, cmd_tests, @@ -223,5 +225,13 @@ def test(op_id, download_logs, use_json): cmd_single_test(data, download_logs, use_json) +@results.command() +@single_build_and_test_options +@results_display_options +def build(op_id, download_logs, use_json): + data = dashboard_fetch_build(op_id, use_json) + cmd_single_build(data, download_logs, use_json) + + if __name__ == "__main__": main_kcidev() diff --git a/kcidev/subcommands/results/parser.py b/kcidev/subcommands/results/parser.py index 4454853..b35c3df 100644 --- a/kcidev/subcommands/results/parser.py +++ b/kcidev/subcommands/results/parser.py @@ -156,12 +156,8 @@ def cmd_builds(data, commit, download_logs, status, count, use_json): log_path = build["log_url"] if download_logs: try: - log_gz = requests.get(build["log_url"]) - log = gzip.decompress(log_gz.content) log_file = f"{build['config_name']}-{build['architecture']}-{build['compiler']}-{commit}.log" - with open(log_file, mode="wb") as file: - file.write(log) - log_path = "file://" + os.path.join(os.getcwd(), log_file) + log_path = download_logs_to_file(build["log_url"], log_file) except: kci_err(f"Failed to fetch log {build['log_url']}.") pass @@ -170,28 +166,7 @@ def cmd_builds(data, commit, download_logs, status, count, use_json): elif use_json: builds.append(create_build_json(build, log_path)) else: - kci_msg_nonl("- config:") - kci_msg_cyan_nonl(build["config_name"]) - kci_msg_nonl(" arch: ") - kci_msg_cyan_nonl(build["architecture"]) - kci_msg_nonl(" compiler: ") - kci_msg_cyan_nonl(build["compiler"]) - kci_msg("") - - kci_msg_nonl(" status:") - if build["status"] == "PASS": - kci_msg_green_nonl("PASS") - elif build["status"] == "FAIL": - kci_msg_red_nonl("FAIL") - else: - kci_msg_yellow_nonl(f"INCONCLUSIVE (status: {build['status']})") - kci_msg("") - - kci_msg(f" config_url: {build['config_url']}") - kci_msg(f" log: {log_path}") - kci_msg(f" id: {build['id']}") - kci_msg(f" dashboard: https://dashboard.kernelci.org/build/{build['id']}") - kci_msg("") + print_build(build, log_path) if count and use_json: kci_msg(f'{{"count":{filtered_builds}}}') elif count: @@ -200,6 +175,31 @@ def cmd_builds(data, commit, download_logs, status, count, use_json): kci_msg(json.dumps(builds)) +def print_build(build, log_path): + kci_msg_nonl("- config:") + kci_msg_cyan_nonl(build["config_name"]) + kci_msg_nonl(" arch: ") + kci_msg_cyan_nonl(build["architecture"]) + kci_msg_nonl(" compiler: ") + kci_msg_cyan_nonl(build["compiler"]) + kci_msg("") + + kci_msg_nonl(" status:") + if build["status"] == "PASS": + kci_msg_green_nonl("PASS") + elif build["status"] == "FAIL": + kci_msg_red_nonl("FAIL") + else: + kci_msg_yellow_nonl(f"INCONCLUSIVE (status: {build['status']})") + kci_msg("") + + kci_msg(f" config_url: {build['config_url']}") + kci_msg(f" log: {log_path}") + kci_msg(f" id: {build['id']}") + kci_msg(f" dashboard: https://dashboard.kernelci.org/build/{build['id']}") + kci_msg("") + + def filter_out_by_status(status, filter): if filter == "all": return False @@ -331,3 +331,16 @@ def cmd_single_test(test, download_logs, use_json): kci_msg(create_test_json(test, log_path)) else: print_test(test, log_path) + + +def cmd_single_build(build, download_logs, use_json): + log_path = build["log_url"] + if download_logs: + log_file = log_file = ( + f"{build['config_name']}-{build['architecture']}-{build['compiler']}-{build['git_commit_hash']}-{build['id']}.log" + ) + log_path = download_logs_to_file(build["log_url"], log_file) + if use_json: + kci_msg(create_build_json(build, log_path)) + else: + print_build(build, log_path)