def save_json(self, package_dir, force=False): """save an entire folder of json (along with the index)""" results = self.get_results() urls = [] # Get top level keys, labels for each labels = list(results.keys()) self._setup_save(package_dir, "json", force) extractor_dir = os.path.join(package_dir, self.name) # Organize results by version inside of separate files for label in labels: result_file = os.path.join(extractor_dir, "%s-%s.json" % (self.name, label)) newresult = {label: results[label]} urls.append(os.path.basename(result_file)) if os.path.exists(result_file) and force is False: logger.warning( "Result file %s already exists and force is False, skipping overwrite." % result_file) continue write_json(newresult, result_file) # Update the index to include the (relative) list of files self.update_index(extractor_dir, {"json": {"urls": urls}})
def check_metrics(self, packages, metrics, outdir, quiet=False): """Given a list of packages and metrics, return versions that are not present. Packages and metrics should each be a list of the same length """ missing = {} for i, package in enumerate(packages): uri, name = package.split(":") # pypi:sif missing[package] = {} # Use a shared manager to get updated versions try: manager = get_named_manager(uri, name) except NotImplementedError: if not quiet: logger.warning("%s is not a valid package manager uri." % package) for metric in metrics[i]: # First look for existing data in outdir index_file = os.path.join(outdir, uri, name, metric, "index.json") if not os.path.exists(index_file): if not quiet: logger.warning( "Index file for %s does not exist, skipping." % package) continue # Load current versions from results results = self.read_metric_local(index_file, metric) current = list(results.keys()) # Change metrics show version ranges if current and ".." in current[0]: current = [ x.split("..")[0] for x in current if "EMPTY" not in x ] + [ x.split("..")[1] for x in current if "EMPTY" not in x ] # Compare found to current to get missing found = [ x.get("version") for x in manager.specs if x.get("version") ] missing[package][metric] = [ x for x in found if x not in current ] # Check for up to date, symbol = "✔️" if missing[package][metric]: symbol = "✖️" if not quiet: print("[%s ] %s metric %s" % (symbol, package, metric)) return missing
def plot_results(self, result_file, outdir=None, force=False, title=None): """Given a metric has a template and a function to generate data for it, create the graph for the user. """ template = os.path.join(self.classpath, "template.html") if os.path.exists(template) and hasattr(self, "get_plot_data"): from caliper.metrics.graphs import generate_graph outdir = outdir or get_tmpdir("%s-graph-" % self.name) data = self.get_plot_data(result_file, title=title) generate_graph(template=template, data=data, outdir=outdir, force=force) else: logger.warning( "A metric must have template.html and get_plot_data.")
def _setup_save(self, package_dir, fmt, force): """Setup any kind of save, meaning creating necessary output directories and the intended filename. """ # Each metric has it's own subfolder extractor_dir = os.path.join(package_dir, self.name) mkdir_p(extractor_dir) # Prepare to write results to file if fmt in ["json-single", "zip"]: fmt = "json" if fmt == "json-single" else fmt outfile = os.path.join(extractor_dir, "%s-results.%s" % (self.name, fmt)) if os.path.exists(outfile) and not force: logger.warning("%s exists and force is False, skipping." % outfile) return return outfile
def update_metrics(self, packages, metrics, outdir): """Given a list of packages and metrics, check and update with new versions""" missing = self.check_metrics(packages, metrics, outdir) for package, metrics in missing.items(): uri, name = package.split(":") # pypi:sif # Use a shared manager to get updated versions try: manager = get_named_manager(uri, name) except NotImplementedError: logger.warning("%s is not a valid package manager uri." % package) pass # deepcopy original specs to update the manger specs = deepcopy(manager.specs) for metric, versions in metrics.items(): if not versions: continue index_file = os.path.join(outdir, uri, name, metric, "index.json") if not os.path.exists(index_file): logger.warning( "Index file for %s does not exist, skipping." % package) continue # Update manager to only have needed versions manager._specs = [ x for x in specs if x.get("version") in versions ] if not manager.specs: continue client = MetricsExtractor(manager=manager) client.extract_metric(metric) # Save results to files client.save_all(outdir, force=True) client.cleanup(force=True)