from __future__ import annotations import unittest from pathlib import Path from PythonModels.components.amesim_pneumatic import HELIUM_PNEUMATIC_GAS, cm3_to_m3 from PythonModels.reporting.amesim_results import load_test_mql_amesim_results from PythonModels.systems.test_mql_pneumatic import ( absolute_pressure_from_amesim_bar_parameter, build_test_mql_pneumatic_assembly, pressure_from_amesim_bar_parameter, pressure_to_amesim_gauge_pa, ) REPO_ROOT = Path(__file__).resolve().parents[1] TEST_MQL_AME = REPO_ROOT / "AmesimModels" / "test_mql.ame" class TestMqlPneumaticAssemblyTests(unittest.TestCase): @classmethod def setUpClass(cls) -> None: cls.amesim_results = load_test_mql_amesim_results(TEST_MQL_AME) def test_assembles_expected_amesim_pneumatic_component_counts(self) -> None: assembly = build_test_mql_pneumatic_assembly() self.assertEqual(len(assembly.fixed_chambers), 4) self.assertEqual(len(assembly.variable_chambers), 8) self.assertEqual(len(assembly.fixed_orifices), 8) self.assertEqual(len(assembly.variable_orifices), 8) self.assertEqual(assembly.component_count, 28) self.assertIn("pn_general_chamber", assembly.aliases) self.assertIn("pn_c1_8", assembly.aliases) self.assertIn("pn_orifice_18", assembly.aliases) self.assertIn("pn_morifice_11", assembly.aliases) def test_uses_amesim_pressure_conventions(self) -> None: assembly = build_test_mql_pneumatic_assembly() self.assertAlmostEqual(absolute_pressure_from_amesim_bar_parameter(153.0), 15300000.0) self.assertAlmostEqual(pressure_from_amesim_bar_parameter(153.0), 15198700.0) self.assertAlmostEqual(pressure_to_amesim_gauge_pa(100000.0), -1300.0) self.assertAlmostEqual(assembly.fixed_initial_absolute_pressure_pa, 15300000.0) self.assertAlmostEqual(assembly.fixed_initial_gauge_pressure_pa, 15198700.0) self.assertAlmostEqual(assembly.variable_initial_absolute_pressure_pa, 100000.0) self.assertAlmostEqual(assembly.variable_initial_gauge_pressure_pa, -1300.0) self.assertAlmostEqual(assembly.initial_pressure_pa, 15198700.0) def test_chamber_parameters_are_resolved_in_si_units(self) -> None: assembly = build_test_mql_pneumatic_assembly() fixed_chamber = assembly.fixed_chambers["pn_general_chamber"] variable_chamber = assembly.variable_chambers["pn_c1_8"] self.assertAlmostEqual(fixed_chamber.volume, 0.057) self.assertAlmostEqual(variable_chamber.dead_volume, 0.015) self.assertAlmostEqual(variable_chamber.volume, 0.015) self.assertIs(fixed_chamber.gas, HELIUM_PNEUMATIC_GAS) self.assertIs(variable_chamber.gas, HELIUM_PNEUMATIC_GAS) self.assertAlmostEqual(fixed_chamber.properties().T, 293.15) self.assertAlmostEqual(variable_chamber.properties().T, 293.15) def test_orifice_parameters_are_resolved_in_si_units(self) -> None: assembly = build_test_mql_pneumatic_assembly() fixed_orifice = assembly.fixed_orifices["pn_orifice_18"] variable_orifice = assembly.variable_orifices["pn_morifice_11"] self.assertAlmostEqual(fixed_orifice.area, 78.5e-6) self.assertAlmostEqual(fixed_orifice.flow_coefficient, 0.9) self.assertAlmostEqual(variable_orifice.area, 78.5e-6) self.assertAlmostEqual(variable_orifice.flow_coefficient, 0.45) self.assertAlmostEqual(variable_orifice.opening, 0.0) self.assertEqual(assembly.variable_orifice_control_count, 8) control = assembly.variable_orifice_controls["pn_morifice_11"] self.assertEqual(control.step.alias, "step_8") self.assertAlmostEqual(control.opening_at(0.0), 0.0) self.assertAlmostEqual(control.opening_at(0.039), 0.0) self.assertAlmostEqual(control.opening_at(0.04), 1.0) assembly.set_variable_orifice_openings(0.04) self.assertAlmostEqual(variable_orifice.opening, 1.0) def test_chamber_initial_observables_match_amesim_results(self) -> None: assembly = build_test_mql_pneumatic_assembly() fixed_chamber = assembly.fixed_chambers["pn_general_chamber"] variable_chamber = assembly.variable_chambers["pn_c1_8"] self.assertAlmostEqual( fixed_chamber.pressure_gauge_pa(), self.amesim_results.series("press@pn_general_chamber")[0], delta=1.0e-8, ) self.assertAlmostEqual( variable_chamber.pressure_gauge_pa(), self.amesim_results.series("press@pn_c1_8")[0], delta=1.0e-8, ) self.assertAlmostEqual( variable_chamber.volume_cm3(), self.amesim_results.series("vol@pn_c1_8")[0], ) self.assertAlmostEqual( variable_chamber.gas_mass_g(), self.amesim_results.series("mgas1@pn_c1_8")[0], delta=1.0e-4, ) def test_variable_chamber_volume_matches_piston_volume_observable(self) -> None: assembly = build_test_mql_pneumatic_assembly() for chamber_alias, chamber in assembly.variable_chambers.items(): piston_alias = chamber_alias.replace("pn_c1", "pn_brp2") with self.subTest(alias=chamber_alias): piston_volume_cm3 = self.amesim_results.series(f"vol1@{piston_alias}")[-1] chamber.set_external_volume_m3(cm3_to_m3(piston_volume_cm3)) self.assertAlmostEqual( chamber.volume_cm3(), self.amesim_results.series(f"vol@{chamber_alias}")[-1], delta=1.0e-6, ) def test_assembled_orifice_can_compute_helium_mass_flow(self) -> None: assembly = build_test_mql_pneumatic_assembly() fixed_orifice = assembly.fixed_orifices["pn_orifice_18"] flow = fixed_orifice.mass_flow(15.0e6, 10.0e6, 293.15) self.assertGreater(flow, 0.0) if __name__ == "__main__": unittest.main()