Beispiel #1
0
def load_plugins():
    """
    Loads declared plugins.
    """
    for entry_point in iter_entry_points(MODEL_PLUGIN_ID):
        plugin_name = entry_point.name
        module_name = entry_point.module_name
        _LOGGER.info("Loading FAST-OAD plugin %s", plugin_name)
        BundleLoader().explore_folder(module_name, is_package=True)
        Variable.read_variable_descriptions(module_name)
Beispiel #2
0
def load_plugins():
    """
    Loads declared plugins.
    """
    for entry_point in iter_entry_points(MODEL_PLUGIN_ID):
        plugin_name = entry_point.name
        module_name = entry_point.module_name
        _recursive_load(module_name)
        _LOGGER.info("Loaded FAST-OAD plugin %s", plugin_name)
        Variable.read_variable_descriptions(module_name)
 def _load_models(cls, plugin_definition: PluginDefinition):
     """Loads models from plugin."""
     if SubPackageNames.MODELS in plugin_definition.subpackages:
         _LOGGER.debug("   Loading models")
         BundleLoader().explore_folder(
             plugin_definition.subpackages[SubPackageNames.MODELS], is_package=True
         )
         Variable.read_variable_descriptions(
             plugin_definition.subpackages[SubPackageNames.MODELS]
         )
def test_register_checks_as_decorator(cleanup):
    log_file_path = pth.join(RESULTS_FOLDER_PATH, "log4.txt")
    set_logger_file(log_file_path)

    @ValidityDomainChecker({"input1": (1.0, 5.0), "output2": (300.0, 500.0)}, "main.dec")
    class Comp1(om.ExplicitComponent):
        def setup(self):
            self.add_input("input1", 0.5, units="km")
            self.add_output("output1", 150.0, units="km/h", upper=130.0)
            self.add_output("output2", 200.0, units="K", lower=0.0)
            self.add_output("output3", 1000.0, units="kg", lower=0.0, upper=5000.0)

    comp = Comp1()

    # Just checking there is no side effect. VariableList.from_system() uses
    # setup(), even if it is made to have no effect, and ValidityDomainChecker
    # modifies setup(), so is is worth checking.
    variables = VariableList.from_system(comp)
    assert len(variables) == 4

    # Now for the real test
    # We test that upper and lower bounds are retrieved from OpenMDAO component,
    # overwritten when required and that units are correctly taken into account.
    comp.setup()

    variables = VariableList(
        [
            Variable("input1", value=3.0, units="m"),
            Variable("output1", value=40.0, units="m/s"),
            Variable("output2", value=310.0, units="degC"),
            Variable("output3", value=6.0, units="t"),
        ]
    )
    records = ValidityDomainChecker.check_variables(variables)
    assert [
        (
            rec.variable_name,
            rec.status,
            rec.limit_value,
            rec.value,
            rec.source_file,
            rec.logger_name,
        )
        for rec in records
    ] == [
        ("input1", ValidityStatus.TOO_LOW, 1.0, 3.0, __file__, "main.dec"),
        ("output1", ValidityStatus.TOO_HIGH, 130.0, 40.0, __file__, "main.dec"),
        ("output2", ValidityStatus.TOO_HIGH, 500.0, 310.0, __file__, "main.dec"),
        ("output3", ValidityStatus.TOO_HIGH, 5000.0, 6.0, __file__, "main.dec"),
    ]

    ValidityDomainChecker.log_records(records)
    with open(log_file_path) as log_file:
        assert len(log_file.readlines()) == 4
Beispiel #5
0
def test_plugins(with_dummy_plugins):

    FastoadLoader._loaded = True  # Ensures next instantiation will NOT trigger reloading

    # Before FastoadLoader.load(), services are not registered
    with pytest.raises(FastBundleLoaderUnknownFactoryNameError):
        declared_dummy_1 = RegisterService.get_provider(
            "test.plugin.declared.1")
    with pytest.raises(FastBundleLoaderUnknownFactoryNameError):
        decorated_dummy_1 = RegisterService.get_provider(
            "test.plugin.decorated.1")

    FastoadLoader._loaded = False  # Ensures next instantiation will trigger reloading

    dist1_definition = FastoadLoader(
    ).distribution_plugin_definitions["dummy-dist-1"]
    assert "models" not in dist1_definition["test_plugin_1"].subpackages
    assert "notebooks" not in dist1_definition["test_plugin_1"].subpackages

    assert "models" not in dist1_definition["test_plugin_4"].subpackages
    assert "configurations" not in dist1_definition[
        "test_plugin_4"].subpackages

    dist2_definition = FastoadLoader(
    ).distribution_plugin_definitions["dummy-dist-2"]
    assert (
        dist2_definition["test_plugin_3"].subpackages[SubPackageNames.MODELS]
        == "tests.dummy_plugins.dist_2.dummy_plugin_3.models")
    assert "notebooks" not in dist2_definition["test_plugin_3"].subpackages
    assert (dist2_definition["test_plugin_3"].subpackages[
        SubPackageNames.CONFIGURATIONS] ==
            "tests.dummy_plugins.dist_2.dummy_plugin_3.configurations")

    declared_dummy_1 = RegisterService.get_provider("test.plugin.declared.1")
    assert declared_dummy_1.my_class() == "DeclaredDummy1"
    declared_dummy_2 = RegisterService.get_provider("test.plugin.declared.2")
    assert declared_dummy_2.my_class() == "DeclaredDummy2"

    decorated_dummy_1 = RegisterService.get_provider("test.plugin.decorated.1")
    assert decorated_dummy_1.my_class() == "DecoratedDummy1"
    decorated_dummy_2 = RegisterService.get_provider("test.plugin.decorated.2")
    assert decorated_dummy_2.my_class() == "DecoratedDummy2"
    # This one is in a subpackage
    decorated_dummy_3 = RegisterService.get_provider("test.plugin.decorated.3")
    assert decorated_dummy_3.my_class() == "DecoratedDummy3"

    # Checking variable description.
    assert Variable("dummy:variable").description == "Some dummy variable."
Beispiel #6
0
def cleanup():
    rmtree(RESULTS_FOLDER_PATH, ignore_errors=True)

    # Need to clean up variable descriptions because it is manipulated in other tests.
    Variable.read_variable_descriptions(pth.dirname(fastoad.models.__file__),
                                        update_existing=False)
Beispiel #7
0
def test_write_outputs():
    problem = FASTOADProblem()
    problem.model.add_subsystem("sellar", Sellar(), promotes=["*"])
    problem.output_file_path = pth.join(RESULTS_FOLDER_PATH, "output.xml")
    problem.setup()

    problem.write_outputs()
    variables = VariableIO(problem.output_file_path).read()
    assert variables == [
        Variable(name="f", value=1.0),
        Variable(name="g1", value=1.0),
        Variable(name="g2", value=1.0),
        Variable(name="x", value=2),
        Variable(name="y2", value=1.0),
        Variable(name="z", value=[5.0, 2.0], units="m**2"),
    ]

    problem.run_model()
    problem.write_outputs()
    variables = VariableIO(problem.output_file_path).read()
    assert variables == [
        Variable(name="f", value=32.569100892077444),
        Variable(name="g1", value=-23.409095627564167),
        Variable(name="g2", value=-11.845478137832359),
        Variable(name="x", value=2),
        Variable(name="y2", value=12.154521862167641),
        Variable(name="z", value=[5.0, 2.0], units="m**2"),
    ]
def test_register_checks_instantiation(cleanup):
    ValidityDomainChecker(
        {
            "var_with_upper_and_lower": (-1.0, 10.0),
            "var_with_lower": (-10.0, None),
            "var_with_upper": (None, 5.0),
        },
        "main.logger1",
    )

    # Now registering is done through instantiation, and with another logger
    ValidityDomainChecker(
        {"var_with_upper_and_lower": (-3.0, 5.0), "var_with_lower": (0.0, None)}, "main.logger2"
    )

    # Third call with same logger as the first one
    ValidityDomainChecker({"other_var": (-10.0, 1.0)}, "main.logger1")

    # Check 1 --------------------------------------------------------------------------------------
    log_file_path = pth.join(RESULTS_FOLDER_PATH, "log1.txt")
    set_logger_file(log_file_path)
    variables = VariableList(
        [
            Variable("var_with_upper_and_lower", value=-2.0, units="m"),  # too low for logger1
            Variable("var_with_lower", value=-1.0),  # too low for logger2
            Variable("var_with_upper", value=10.0),  # too high, only for logger1
            Variable("other_var", value=1.1),  # too high, only for logger1 (second registering)
            Variable("unbound_var", value=42.0),
        ]
    )

    records = ValidityDomainChecker.check_variables(variables)
    assert [
        (
            rec.variable_name,
            rec.status,
            rec.limit_value,
            rec.value,
            rec.source_file,
            rec.logger_name,
        )
        for rec in records
    ] == [
        ("var_with_upper_and_lower", ValidityStatus.TOO_LOW, -1.0, -2.0, __file__, "main.logger1"),
        ("var_with_upper_and_lower", ValidityStatus.OK, None, -2.0, __file__, "main.logger2"),
        ("var_with_lower", ValidityStatus.OK, None, -1.0, __file__, "main.logger1"),
        ("var_with_lower", ValidityStatus.TOO_LOW, 0.0, -1.0, __file__, "main.logger2"),
        ("var_with_upper", ValidityStatus.TOO_HIGH, 5.0, 10.0, __file__, "main.logger1"),
        ("other_var", ValidityStatus.TOO_HIGH, 1.0, 1.1, __file__, "main.logger1"),
    ]

    ValidityDomainChecker.log_records(records)
    with open(log_file_path) as log_file:
        assert len(log_file.readlines()) == 4

    # Check 2 --------------------------------------------------------------------------------------
    log_file_path = pth.join(RESULTS_FOLDER_PATH, "log2.txt")
    set_logger_file(log_file_path)
    variables = VariableList(
        [
            Variable("other_var", value=-11.0),  # too low, only for logger1 (second registering)
            Variable("var_with_lower", value=-15.0),  # too low for logger1 and logger2
            Variable("var_with_upper", value=0.0),  # Ok
            Variable("unbound_var", value=1e42),
            Variable("var_with_upper_and_lower", value=7.0),  # too high for logger2
        ]
    )

    records = ValidityDomainChecker.check_variables(variables)
    assert [
        (
            rec.variable_name,
            rec.status,
            rec.limit_value,
            rec.value,
            rec.source_file,
            rec.logger_name,
        )
        for rec in records
    ] == [
        ("other_var", ValidityStatus.TOO_LOW, -10.0, -11.0, __file__, "main.logger1"),
        ("var_with_lower", ValidityStatus.TOO_LOW, -10.0, -15.0, __file__, "main.logger1"),
        ("var_with_lower", ValidityStatus.TOO_LOW, 0.0, -15.0, __file__, "main.logger2"),
        ("var_with_upper", ValidityStatus.OK, None, 0.0, __file__, "main.logger1"),
        ("var_with_upper_and_lower", ValidityStatus.OK, None, 7.0, __file__, "main.logger1"),
        ("var_with_upper_and_lower", ValidityStatus.TOO_HIGH, 5.0, 7.0, __file__, "main.logger2"),
    ]

    ValidityDomainChecker.log_records(records)
    with open(log_file_path) as log_file:
        assert len(log_file.readlines()) == 4

    # Check 3 --------------------------------------------------------------------------------------
    log_file_path = pth.join(RESULTS_FOLDER_PATH, "log3.txt")
    set_logger_file(log_file_path)
    variables = VariableList(
        [
            Variable("var_with_upper_and_lower", value=1.0),  # Ok
            Variable("other_var", value=-5.0),  # Ok
            Variable("unbound_var", value=-1e42),
            Variable("var_with_lower", value=1.0),  # Ok
        ]
    )

    records = ValidityDomainChecker.check_variables(variables)
    assert [
        (
            rec.variable_name,
            rec.status,
            rec.limit_value,
            rec.value,
            rec.source_file,
            rec.logger_name,
        )
        for rec in records
    ] == [
        ("var_with_upper_and_lower", ValidityStatus.OK, None, 1.0, __file__, "main.logger1"),
        ("var_with_upper_and_lower", ValidityStatus.OK, None, 1.0, __file__, "main.logger2"),
        ("other_var", ValidityStatus.OK, None, -5.0, __file__, "main.logger1"),
        ("var_with_lower", ValidityStatus.OK, None, 1.0, __file__, "main.logger1"),
        ("var_with_lower", ValidityStatus.OK, None, 1.0, __file__, "main.logger2"),
    ]

    ValidityDomainChecker.log_records(records)
    with open(log_file_path) as log_file:
        assert len(log_file.readlines()) == 0
def test_write_outputs():
    problem = FASTOADProblem()
    problem.model.add_subsystem("sellar", Sellar(), promotes=["*"])
    problem.output_file_path = pth.join(RESULTS_FOLDER_PATH, "output.xml")
    problem.setup()

    problem.write_outputs()
    variables = VariableIO(problem.output_file_path).read()
    assert variables == [
        Variable(name="f", val=1.0),
        Variable(name="g1", val=1.0),
        Variable(name="g2", val=1.0),
        Variable(name="x", val=2.0),
        Variable(name="y2", val=1.0),
        Variable(name="z", val=[np.nan, np.nan], units="m**2"),
    ]

    problem["x"] = 2.0
    problem["z"] = [
        5.0,
        2.0,
    ]  # Since version 3.17 of OpenMDAO, the np.nan input definition of z is chosen.

    problem.run_model()
    problem.write_outputs()
    variables = VariableIO(problem.output_file_path).read()
    assert variables == [
        Variable(name="f", val=32.569100892077444),
        Variable(name="g1", val=-23.409095627564167),
        Variable(name="g2", val=-11.845478137832359),
        Variable(name="x", val=2.0),
        Variable(name="y2", val=12.154521862167641),
        Variable(name="z", val=[5.0, 2.0], units="m**2"),
    ]