Source code for idmtools.core.experiment_factory

"""
Define ExperimentFactory.

This is used mostly internally. It does allow us to support specialized experiment types when needed.

Copyright 2021, Bill & Melinda Gates Foundation. All rights reserved.
"""
from logging import getLogger, DEBUG
from idmtools.entities.experiment import Experiment
from idmtools.registry import experiment_specification

logger = getLogger(__name__)


[docs]class ExperimentFactory: """ ExperimentFactory allows creating experiments that could be derived through plugins. """ DEFAULT_KEY = 'idmtools.entities.experiment.Experiment'
[docs] def __init__(self): """ Initialize our factory. On initialize, we load our plugin and build a map of ids for experiments. """ from idmtools.registry.experiment_specification import ExperimentPlugins self._builders = ExperimentPlugins().get_plugin_map() aliases = dict() # register types as full paths as well for _model, spec in self._builders.items(): aliases[f'{spec.get_type().__module__}.{spec.get_type().__name__}'] = spec self._builders.update(aliases)
[docs] def create(self, key, fallback=None, **kwargs) -> Experiment: # noqa: F821 """ Create an experiment of type key. Args: key: Experiment Type fallback: Fallback type. If none, uses DEFAULT_KEY **kwargs: Options to pass to the experiment object Returns: Experiment object that was created """ if logger.isEnabledFor(DEBUG): logger.debug(f"Attempting to create experiment of type {key}") if not key: key = self.DEFAULT_KEY else: logger.warning(f'Experiment type: {key}') if key not in self._builders: if not fallback: raise ValueError(f"The ExperimentFactory could not create an experiment of type {key}") else: logger.warning(f'Could not find experiment type {key}. Using Fallback type of {fallback.__class__}') return fallback() model_spec: experiment_specification = self._builders.get(key) result = model_spec.get(kwargs) if logger.isEnabledFor(DEBUG): logger.debug(f"Experiment created for type {key}") return result
experiment_factory = ExperimentFactory()