def AddRunsFromDirectory(self, path, name=None): """Load runs from a directory; recursively walks subdirectories. If path doesn't exist, no-op. This ensures that it is safe to call `AddRunsFromDirectory` multiple times, even before the directory is made. If path is a directory, load event files in the directory (if any exist) and recursively call AddRunsFromDirectory on any subdirectories. This mean you can call AddRunsFromDirectory at the root of a tree of event logs and TensorBoard will load them all. If the `EventMultiplexer` is already loaded this will cause the newly created accumulators to `Reload()`. Args: path: A string path to a directory to load runs from. name: Optionally, what name to apply to the runs. If name is provided and the directory contains run subdirectories, the name of each subrun is the concatenation of the parent name and the subdirectory name. If name is provided and the directory contains event files, then a run is added called "name" and with the events from the path. Raises: ValueError: If the path exists and isn't a directory. Returns: The `EventMultiplexer`. """ logger.info("Starting AddRunsFromDirectory: %s", path) for subdir in io_wrapper.GetLogdirSubdirectories(path): logger.info("Adding run from directory %s", subdir) rpath = os.path.relpath(subdir, path) subname = os.path.join(name, rpath) if name else rpath self.AddRun(subdir, name=subname) logger.info("Done with AddRunsFromDirectory: %s", path) return self
def generators_from_logdir(logdir): """Returns a list of event generators for subdirectories with event files. The number of generators returned should equal the number of directories within logdir that contain event files. If only logdir contains event files, returns a list of length one. Args: logdir: A log directory that contains event files. Returns: List of event generators for each subdirectory with event files. """ subdirs = io_wrapper.GetLogdirSubdirectories(logdir) generators = [ itertools.chain( *[ generator_from_event_file(os.path.join(subdir, f)) for f in tf.io.gfile.listdir(subdir) if io_wrapper.IsTensorFlowEventsFile(os.path.join(subdir, f)) ] ) for subdir in subdirs ] return generators
def AddRunsFromDirectory(self, path, name=None): """Load runs from a directory; recursively walks subdirectories. If path doesn't exist, no-op. This ensures that it is safe to call `AddRunsFromDirectory` multiple times, even before the directory is made. Args: path: A string path to a directory to load runs from. name: Optional, specifies a name for the experiment under which the runs from this directory hierarchy will be imported. If omitted, the path will be used as the name. Raises: ValueError: If the path exists and isn't a directory. """ logger.info("Starting AddRunsFromDirectory: %s (as %s)", path, name) for subdir in io_wrapper.GetLogdirSubdirectories(path): logger.info("Processing directory %s", subdir) if subdir not in self._run_loaders: logger.info("Creating DB loader for directory %s", subdir) names = self._get_exp_and_run_names(path, subdir, name) experiment_name, run_name = names self._run_loaders[subdir] = _RunLoader( subdir=subdir, experiment_name=experiment_name, run_name=run_name) logger.info("Done with AddRunsFromDirectory: %s", path)
def AddRunsFromDirectory(self, path, name=None): """Load runs from a directory; recursively walks subdirectories. If path doesn't exist, no-op. This ensures that it is safe to call `AddRunsFromDirectory` multiple times, even before the directory is made. Args: path: A string path to a directory to load runs from. name: Optional, specifies a name for the experiment under which the runs from this directory hierarchy will be imported. If omitted, the path will be used as the name. Raises: ValueError: If the path exists and isn't a directory. """ tf.logging.info('Starting AddRunsFromDirectory: %s (as %s)', path, name) for subdir in io_wrapper.GetLogdirSubdirectories(path): tf.logging.info('Processing directory %s', subdir) if subdir not in self._run_importers: tf.logging.info('Creating DB importer for directory %s', subdir) self._run_importers[subdir] = _RunImporter( db_path=self._db_path, subdir=subdir, experiment_name=(name or path), run_name=os.path.relpath(subdir, path)) tf.logging.info('Done with AddRunsFromDirectory: %s', path)
def get_inspection_units(logdir="", event_file="", tag=""): """Returns a list of InspectionUnit objects given either logdir or event_file. If logdir is given, the number of InspectionUnits should equal the number of directories or subdirectories that contain event files. If event_file is given, the number of InspectionUnits should be 1. Args: logdir: A log directory that contains event files. event_file: Or, a particular event file path. tag: An optional tag name to query for. Returns: A list of InspectionUnit objects. """ if logdir: subdirs = io_wrapper.GetLogdirSubdirectories(logdir) inspection_units = [] for subdir in subdirs: generator = itertools.chain( *[ generator_from_event_file(os.path.join(subdir, f)) for f in tf.io.gfile.listdir(subdir) if io_wrapper.IsTensorFlowEventsFile(os.path.join(subdir, f)) ] ) inspection_units.append( InspectionUnit( name=subdir, generator=generator, field_to_obs=get_field_to_observations_map(generator, tag), ) ) if inspection_units: print( "Found event files in:\n{}\n".format( "\n".join([u.name for u in inspection_units]) ) ) elif io_wrapper.IsTensorFlowEventsFile(logdir): print( "It seems that {} may be an event file instead of a logdir. If this " "is the case, use --event_file instead of --logdir to pass " "it in.".format(logdir) ) else: print("No event files found within logdir {}".format(logdir)) return inspection_units elif event_file: generator = generator_from_event_file(event_file) return [ InspectionUnit( name=event_file, generator=generator, field_to_obs=get_field_to_observations_map(generator, tag), ) ] return []
def testGetLogdirSubdirectories(self): temp_dir = tempfile.mkdtemp(prefix=self.get_temp_dir()) self._CreateDeepDirectoryStructure(temp_dir) # Only subdirectories that immediately contains at least 1 events # file should be listed. expected = [ '', 'bar', 'bar/baz', 'quuz', 'quuz/garply', 'quuz/garply/corge', 'quuz/garply/grault', 'waldo/fred', ] self.assertItemsEqual( [(os.path.join(temp_dir, subdir) if subdir else temp_dir) for subdir in expected], io_wrapper.GetLogdirSubdirectories(temp_dir))
def synchronize_runs(self): """Finds new runs within `logdir` and makes `DirectoryLoaders` for them. In addition, any existing `DirectoryLoader` whose run directory no longer exists will be deleted. """ logger.info('Starting logdir traversal of %s', self._logdir) runs_seen = set() for subdir in io_wrapper.GetLogdirSubdirectories(self._logdir): run = os.path.relpath(subdir, self._logdir) runs_seen.add(run) if run not in self._directory_loaders: logger.info('- Adding run for relative directory %s', run) self._directory_loaders[run] = self._directory_loader_factory( subdir) stale_runs = set(self._directory_loaders) - runs_seen if stale_runs: for run in stale_runs: logger.info('- Removing run for relative directory %s', run) del self._directory_loaders[run] logger.info('Ending logdir traversal of %s', self._logdir)
def iter_events(root_path): """Returns an iterator that yields (dir, digest, reader) tuples. For each yielded events dir, `digest` changes whenever events have been written to the dir. `reader` is an instance of ScalarReader that can be used to read scalars in dir. """ ensure_tf_logging_patched() try: from tensorboard.backend.event_processing import io_wrapper except ImportError: pass else: for subdir_path in io_wrapper.GetLogdirSubdirectories(root_path): if _linked_resource_path(subdir_path, root_path): log.debug("skipping linked resource path %s", subdir_path) continue digest = _event_files_digest(subdir_path) yield subdir_path, digest, ScalarReader(subdir_path)
def _maybe_scalars(self, fields, run): from tensorboard.backend.event_processing import io_wrapper from tensorboard.backend.event_processing import event_accumulator from guild import tfevent tfevent.ensure_tf_logging_patched() scalars = {} scalar_aliases = self._init_scalar_aliases(run) for path in io_wrapper.GetLogdirSubdirectories(run.path): if not self._path_in_run(path, run): log.debug("%s is not part of run %s, skipping", path, run.id) continue events_checksum_field_name = self._events_checksum_field_name(path) last_checksum = fields.get(events_checksum_field_name) cur_checksum = self._events_checksum(path) log.debug("event path checksums for %s: last=%s, cur=%s", path, last_checksum, cur_checksum) if last_checksum != cur_checksum: log.debug("indexing events in %s", path) rel_path = os.path.relpath(path, run.path) events = event_accumulator._GeneratorFromPath(path).Load() scalar_vals = self._scalar_vals(events, rel_path) self._apply_scalar_vals(scalar_vals, scalars, scalar_aliases) scalars[events_checksum_field_name] = cur_checksum return scalars