diff --git a/curifactory/manager.py b/curifactory/manager.py index f7d39d2..7717eba 100644 --- a/curifactory/manager.py +++ b/curifactory/manager.py @@ -6,6 +6,7 @@ import logging import multiprocessing as mp import os +import shutil import sys from datetime import datetime from socket import gethostname @@ -603,15 +604,29 @@ def generate_report(self): self.store() - reporting.run_report(self, self.reports_path, "_latest", self.report_css_path) + # generate the named report self.live_report_paths = reporting.run_report( self, self.reports_path, self.get_reference_name(), self.report_css_path ) self.live_report_path_generated = True + + # link it into the "_latest" report + report_path = os.path.join(self.reports_path, self.get_reference_name()) + latest_path = os.path.join(self.reports_path, "_latest") + if os.path.exists(latest_path): + if os.path.isfile(latest_path) or os.path.islink(latest_path): + os.remove(latest_path) + else: + shutil.rmtree(latest_path) + logging.info("Linking report to '%s'" % latest_path) + os.symlink(self.get_reference_name(), latest_path, target_is_directory=True) + + # if this is a full store run, _copy_ the output to the new folder if self.store_full: - reporting.run_report( - self, self.get_run_output_path(), "report", self.report_css_path - ) + stored_report_path = os.path.join(self.get_run_output_path(), "report") + logging.info("Copying report to '%s'" % stored_report_path) + shutil.copytree(report_path, stored_report_path) + reporting.update_report_index( self.config["experiments_module_name"], self.reports_path ) diff --git a/test/test_reporting.py b/test/test_reporting.py index 9f40b99..bb23e75 100644 --- a/test/test_reporting.py +++ b/test/test_reporting.py @@ -7,6 +7,7 @@ import curifactory as cf from curifactory import reporting from curifactory.caching import JsonCacher, PickleCacher +from curifactory.experiment import run_experiment from curifactory.reporting import JsonReporter, _add_record_subgraph, render_reportable @@ -144,3 +145,27 @@ def test_fallback_css_used(configured_test_manager): assert os.path.exists( f"{configured_test_manager.reports_path}/{configured_test_manager.get_reference_name()}/style.css" ) + + +def test_all_relevant_reports_generated(configured_test_manager): + """When a store full run of an experiment occurs, the regular report should exist, the linked + "_latest" should exist, and the full store output should have a copy.""" + + configured_test_manager.store_full = True + run_experiment( + "simple_cache", + ["simple_cache"], + param_set_names=["thing1", "thing2"], + mngr=configured_test_manager, + store_full=True, + ) + + assert os.path.exists( + f"{configured_test_manager.reports_path}/{configured_test_manager.get_reference_name()}/index.html" + ) + + assert os.path.exists(f"{configured_test_manager.reports_path}/_latest/index.html") + + assert os.path.exists( + f"{configured_test_manager.get_run_output_path()}/report/index.html" + )