def test_properties():
    """Tests that ProxySimulatorControls implements properties"""

    mock_sim_controls = mock.create_autospec(spec=AbstractSimulatorControls)
    mock_aircraft_controls = mock.create_autospec(spec=ProxyAircraftControls)
    properties_mock = mock.PropertyMock()
    properties_mock.return_value = _TEST_SIM_PROPERTIES
    type(mock_sim_controls).properties = properties_mock

    # Test call to _sim_controls.properties when not in agent mode

    proxy_simulator_controls = ProxySimulatorControls(mock_sim_controls,
                                                      mock_aircraft_controls)
    props = proxy_simulator_controls.properties
    assert isinstance(props, SimProperties)
    assert props == _TEST_SIM_PROPERTIES
    properties_mock.assert_called_once()

    # Test call to _sim_controls.properties when in agent mode

    properties_mock.reset_mock()
    proxy_simulator_controls = ProxySimulatorControls(mock_sim_controls,
                                                      mock_aircraft_controls)
    props = proxy_simulator_controls.properties
    assert isinstance(props, SimProperties)
    assert props == _TEST_SIM_PROPERTIES
    properties_mock.assert_called_once()
Beispiel #2
0
    def __init__(
        self, sim_client: AbstractSimClient, metrics_providers: MetricsProviders
    ):
        self._logger = logging.getLogger(__name__)

        # The actual sim_client
        self._sim_client: AbstractSimClient = sim_client

        # The proxy implementations
        self._proxy_aircraft_controls = ProxyAircraftControls(self._sim_client.aircraft)
        self._proxy_simulator_controls = ProxySimulatorControls(
            self._sim_client.simulation, self._proxy_aircraft_controls
        )

        self.metrics_providers = metrics_providers
def test_step():
    """Tests that ProxySimulatorControls implements step"""

    mock_sim_controls = mock.Mock()
    mock_aircraft_controls = mock.Mock()
    proxy_simulator_controls = ProxySimulatorControls(mock_sim_controls,
                                                      mock_aircraft_controls)

    # Test error message when no sector set

    res = proxy_simulator_controls.step()
    assert res == "No scenario set"

    # Test error handling from step

    proxy_simulator_controls._scenario = "test"
    mock_sim_controls.step = mock.Mock(return_value="Error")
    res = proxy_simulator_controls.step()
    assert res == "Error"

    # Test valid response

    mock_sim_controls.properties = _TEST_SIM_PROPERTIES
    mock_sim_controls.step = mock.Mock(sepc=AbstractSimulatorControls.step,
                                       return_value=None)
    _mock_logger = mock.Mock(spec=logging.Logger)
    proxy_simulator_controls._logger = _mock_logger
    res = proxy_simulator_controls.step()
    assert not res
def test_stop():
    """Tests that ProxySimulatorControls implements stop"""

    mock_sim_controls = mock.create_autospec(spec=AbstractSimulatorControls)
    mock_aircraft_controls = mock.create_autospec(spec=ProxyAircraftControls)
    proxy_simulator_controls = ProxySimulatorControls(mock_sim_controls,
                                                      mock_aircraft_controls)

    # Test error handling from stop
    mock_sim_controls.stop = mock.Mock(sepc=AbstractSimulatorControls.stop,
                                       return_value="Error")
    res = proxy_simulator_controls.stop()
    assert res == "Error"

    # Test valid response
    mock_sim_controls.stop = mock.Mock(sepc=AbstractSimulatorControls.stop,
                                       return_value=None)
    res = proxy_simulator_controls.stop()
    assert not res
def test_set_speed():
    """Tests that ProxySimulatorControls implements set_speed"""

    mock_sim_controls = mock.create_autospec(spec=AbstractSimulatorControls)
    mock_aircraft_controls = mock.create_autospec(spec=ProxyAircraftControls)
    proxy_simulator_controls = ProxySimulatorControls(mock_sim_controls,
                                                      mock_aircraft_controls)

    # Test error handling from set_speed
    mock_sim_controls.set_speed = mock.Mock(
        sepc=AbstractSimulatorControls.set_speed, return_value="Error")
    res = proxy_simulator_controls.set_speed(1.0)
    assert res == "Error"

    # Test set_speed
    mock_sim_controls.properties = _TEST_SIM_PROPERTIES
    mock_sim_controls.set_speed = mock.Mock(
        sepc=AbstractSimulatorControls.set_speed, return_value=None)
    res = proxy_simulator_controls.set_speed(1.0)
    assert not res
    mock_sim_controls.set_speed.assert_called_once_with(1.0)
def test_load_scenario(tmpdir):

    data_dir = Path(tmpdir)
    Settings.DATA_DIR = data_dir

    mock_sim_controls = mock.Mock()
    mock_aircraft_controls = mock.Mock()
    proxy_simulator_controls = ProxySimulatorControls(mock_sim_controls,
                                                      mock_aircraft_controls)

    # Test error when no sector set

    res = proxy_simulator_controls.load_scenario(_TEST_SCENARIO)
    assert res == "No sector set"

    # First test uploading a new scenario

    # Test error handling from reset

    mock_sim_controls.reset.return_value = "Sim error (reset)"
    err = proxy_simulator_controls.load_sector(_TEST_SECTOR)
    assert err == "Sim error (reset)"

    # Test error handling from load_scenario

    proxy_simulator_controls.sector = _TEST_SECTOR
    mock_sim_controls.reset.return_value = None
    mock_sim_controls.load_scenario.return_value = "Sim error (load_scenario)"
    err = proxy_simulator_controls.load_scenario(_TEST_SCENARIO)
    assert err == "Sim error (load_scenario)"

    # Test valid response

    mock_sim_controls.load_scenario.return_value = None
    err = proxy_simulator_controls.load_scenario(_TEST_SCENARIO)
    assert not err

    # Assert scenario saved to file

    with open(data_dir / "scenarios" / f"{_TEST_SCENARIO.name}.json") as f:
        assert json.load(f) == _TEST_SCENARIO.content

    # Test load of existing scenario by name

    existing_scn = Scenario(_TEST_SCENARIO.name, None)
    err = proxy_simulator_controls.load_scenario(existing_scn)
    assert not err
def test_reset():
    """Tests that ProxySimulatorControls implements reset"""

    mock_sim_controls = mock.create_autospec(spec=AbstractSimulatorControls)
    mock_aircraft_controls = mock.create_autospec(spec=ProxyAircraftControls)
    proxy_simulator_controls = ProxySimulatorControls(mock_sim_controls,
                                                      mock_aircraft_controls)

    # Test error handling from reset

    mock_sim_controls.reset = mock.Mock(sepc=AbstractSimulatorControls.reset,
                                        return_value="Error")

    res = proxy_simulator_controls.reset()
    assert res == "Error"

    # Test valid response

    mock_sim_controls.properties = _TEST_SIM_PROPERTIES
    mock_sim_controls.reset = mock.Mock(sepc=AbstractSimulatorControls.reset,
                                        return_value=None)

    res = proxy_simulator_controls.reset()
    assert not res
def test_load_sector(tmpdir):

    data_dir = Path(tmpdir)
    Settings.DATA_DIR = data_dir

    mock_sim_controls = mock.Mock()
    mock_aircraft_controls = mock.Mock()
    proxy_simulator_controls = ProxySimulatorControls(mock_sim_controls,
                                                      mock_aircraft_controls)

    # First test uploading a new sector

    # Test error handling from reset

    mock_sim_controls.reset.return_value = "Sim error (reset)"
    err = proxy_simulator_controls.load_sector(_TEST_SECTOR)
    assert err == "Sim error (reset)"

    # Test error handling from load_sector

    mock_sim_controls.reset.return_value = None
    mock_sim_controls.load_sector.return_value = "Sim error (load_sector)"
    err = proxy_simulator_controls.load_sector(_TEST_SECTOR)
    assert err == "Sim error (load_sector)"

    # Test valid response

    mock_sim_controls.load_sector.return_value = None
    err = proxy_simulator_controls.load_sector(_TEST_SECTOR)
    assert not err

    # Assert sector saved to file

    with open(data_dir / "sectors" / f"{_TEST_SECTOR.name}.geojson") as f:
        assert geojson.dumps(SectorElement.deserialise(f)) == geojson.dumps(
            _TEST_SECTOR.element)

    # Test load of existing sector by name

    existing_sector = Sector(_TEST_SECTOR.name, None)
    err = proxy_simulator_controls.load_sector(existing_sector)
    assert not err
def test_store_data(tmpdir):

    mock_sim_controls = mock.create_autospec(spec=AbstractSimulatorControls)
    mock_aircraft_controls = mock.create_autospec(spec=ProxyAircraftControls)
    proxy_simulator_controls = ProxySimulatorControls(mock_sim_controls,
                                                      mock_aircraft_controls)

    # Set the scenario and sector

    proxy_simulator_controls.sector = _TEST_SECTOR
    mock_sim_controls.reset.return_value = None
    mock_sim_controls.load_scenario.return_value = None
    err = proxy_simulator_controls.load_scenario(_TEST_SCENARIO)
    assert not err

    # Assert exceptions are caught

    Settings.DATA_DIR = "fake"
    err = proxy_simulator_controls.store_data()
    assert err.startswith("Error storing data: ")

    # Assert .last_sector created

    data_dir = Path(tmpdir)
    Settings.DATA_DIR = data_dir

    err = proxy_simulator_controls.store_data()
    assert not err

    with open(tmpdir / "sectors" / ".last_sector") as f:
        assert f.read() == "test-sector\n"

    # Assert .last_scenario created

    with open(tmpdir / "scenarios" / ".last_scenario") as f:
        assert f.read() == "test-scenario\n"
Beispiel #10
0
class SimProxy(AbstractSimClient):
    """
    Class which intercepts any requests before forwarding them to the sim client. Allows
    any actions to be taken which are independent of the particular sim client
    """

    @property
    def aircraft(self) -> ProxyAircraftControls:
        return self._proxy_aircraft_controls

    @property
    def simulation(self) -> ProxySimulatorControls:
        return self._proxy_simulator_controls

    @property
    def sim_version(self) -> VersionInfo:
        return self._sim_client.sim_version

    def __init__(
        self, sim_client: AbstractSimClient, metrics_providers: MetricsProviders
    ):
        self._logger = logging.getLogger(__name__)

        # The actual sim_client
        self._sim_client: AbstractSimClient = sim_client

        # The proxy implementations
        self._proxy_aircraft_controls = ProxyAircraftControls(self._sim_client.aircraft)
        self._proxy_simulator_controls = ProxySimulatorControls(
            self._sim_client.simulation, self._proxy_aircraft_controls
        )

        self.metrics_providers = metrics_providers

    def connect(self, timeout: int = 1) -> None:
        self._sim_client.connect(timeout)

    def start_timers(self) -> List[Timer]:
        return [
            *self._sim_client.start_timers(),
            *self._proxy_simulator_controls.start_timers(),
        ]

    def pre_fetch_data(self):
        """Called on startup to fetch the initial state"""
        _ = self._sim_client.aircraft.all_properties
        _ = self._sim_client.simulation.properties

    def shutdown(self, shutdown_sim: bool = False) -> bool:
        """
        Shutdown the sim client
        :param shutdown_sim: If true, and if the simulation server supports it, will
        also send a shutdown command
        :return: If shutdown_sim was requested, the return value will indicate whether
        the simulator was shut down successfully. Always returns True if shutdown_sim
        was not requested
        """
        err = self._proxy_simulator_controls.store_data()
        if err:
            self._logger.error(err)
        return self._sim_client.shutdown(shutdown_sim)

    def call_metric_function(
        self, provider: AbstractMetricsProvider, metric_name: str, args: list
    ):
        """Calls the metric specified"""
        # NOTE(rkm 2020-01-12) We pass the aircraft and simulator control objects to any
        # metric which is called so that it can have access to any property it needs
        return provider(
            metric_name,
            *args,
            aircraft_controls=self._proxy_aircraft_controls,
            simulator_controls=self._proxy_simulator_controls
        )
def test_abstract_class_implemented():
    """Tests that ProxySimulatorControls implements the abstract base class"""
    ProxySimulatorControls(mock.Mock(), mock.Mock())