isar 1.33.0__tar.gz → 1.33.2__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of isar might be problematic. Click here for more details.
- {isar-1.33.0 → isar-1.33.2}/PKG-INFO +1 -1
- {isar-1.33.0 → isar-1.33.2}/src/isar/apis/schedule/scheduling_controller.py +21 -52
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/settings.py +5 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/models/events.py +45 -26
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/service_connections/mqtt/mqtt_client.py +46 -10
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/service_connections/mqtt/robot_heartbeat_publisher.py +3 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/utilities/scheduling_utilities.py +3 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/state_machine.py +6 -3
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/monitor.py +1 -3
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/returning_home.py +9 -12
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/stopping.py +33 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/functions/pause.py +1 -1
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/functions/resume.py +1 -1
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/functions/start_mission.py +3 -3
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/functions/stop.py +3 -30
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/mission.py +0 -2
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/return_home.py +1 -1
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/utils/common_event_handlers.py +10 -13
- isar-1.33.2/src/isar/storage/blob_storage.py +101 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/storage/local_storage.py +21 -11
- {isar-1.33.0 → isar-1.33.2}/src/isar/storage/storage_interface.py +27 -6
- {isar-1.33.0 → isar-1.33.2}/src/isar/storage/uploader.py +30 -13
- {isar-1.33.0 → isar-1.33.2}/src/isar.egg-info/PKG-INFO +1 -1
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/telemetry/mqtt_client.py +62 -6
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/telemetry/payloads.py +4 -2
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/utilities/json_service.py +6 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/models/communication/test_events.py +3 -3
- {isar-1.33.0 → isar-1.33.2}/tests/isar/services/utilities/test_queue_utilities.py +2 -2
- {isar-1.33.0 → isar-1.33.2}/tests/isar/services/utilities/test_scheduling_utilities.py +1 -1
- {isar-1.33.0 → isar-1.33.2}/tests/isar/state_machine/test_state_machine.py +1 -1
- isar-1.33.0/src/isar/storage/blob_storage.py +0 -79
- {isar-1.33.0 → isar-1.33.2}/.dockerignore +0 -0
- {isar-1.33.0 → isar-1.33.2}/.env.test +0 -0
- {isar-1.33.0 → isar-1.33.2}/.github/ISSUE_TEMPLATE/bug_report.md +0 -0
- {isar-1.33.0 → isar-1.33.2}/.github/ISSUE_TEMPLATE/feature.md +0 -0
- {isar-1.33.0 → isar-1.33.2}/.github/ISSUE_TEMPLATE/improvement.md +0 -0
- {isar-1.33.0 → isar-1.33.2}/.github/PULL_REQUEST_TEMPLATE.md +0 -0
- {isar-1.33.0 → isar-1.33.2}/.github/release.yml +0 -0
- {isar-1.33.0 → isar-1.33.2}/.github/workflows/compile_requirements.yml +0 -0
- {isar-1.33.0 → isar-1.33.2}/.github/workflows/project_automations.yml +0 -0
- {isar-1.33.0 → isar-1.33.2}/.github/workflows/pythonpackage.yml +0 -0
- {isar-1.33.0 → isar-1.33.2}/.github/workflows/pythonpublish.yml +0 -0
- {isar-1.33.0 → isar-1.33.2}/.github/workflows/stale.yml +0 -0
- {isar-1.33.0 → isar-1.33.2}/.gitignore +0 -0
- {isar-1.33.0 → isar-1.33.2}/.pre-commit-config.yaml +0 -0
- {isar-1.33.0 → isar-1.33.2}/LICENSE +0 -0
- {isar-1.33.0 → isar-1.33.2}/README.md +0 -0
- {isar-1.33.0 → isar-1.33.2}/SECURITY.md +0 -0
- {isar-1.33.0 → isar-1.33.2}/docs/Makefile +0 -0
- {isar-1.33.0 → isar-1.33.2}/docs/full_state_machine_diagram.png +0 -0
- {isar-1.33.0 → isar-1.33.2}/docs/make.bat +0 -0
- {isar-1.33.0 → isar-1.33.2}/docs/mission_state_machine_diagram.png +0 -0
- {isar-1.33.0 → isar-1.33.2}/docs/robot_status_state_machine_diagram.png +0 -0
- {isar-1.33.0 → isar-1.33.2}/docs/rst_processing.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/docs/source/conf.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/docs/source/index.rst +0 -0
- {isar-1.33.0 → isar-1.33.2}/docs/source/readme_link.md +0 -0
- {isar-1.33.0 → isar-1.33.2}/docs/update_state_diagram.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/main.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/pyproject.toml +0 -0
- {isar-1.33.0 → isar-1.33.2}/radixconfig.yml +0 -0
- {isar-1.33.0 → isar-1.33.2}/requirements.txt +0 -0
- {isar-1.33.0 → isar-1.33.2}/setup.cfg +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/apis/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/apis/api.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/apis/models/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/apis/models/models.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/apis/models/start_mission_definition.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/apis/robot_control/robot_controller.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/apis/schedule/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/apis/security/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/apis/security/authentication.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/certs/ca-cert.pem +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/configuration_error.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/keyvault/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/keyvault/keyvault_error.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/keyvault/keyvault_service.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/log.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/logging.conf +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/maps/JSP1_intermediate_deck.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/maps/JSP1_weather_deck.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/maps/default_map.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/maps/klab_b.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/maps/klab_compressor.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/maps/klab_turtlebot.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/maps/turtleworld.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/open_telemetry.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/predefined_mission_definition/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/predefined_mission_definition/default_exr.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/predefined_mission_definition/default_mission.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/predefined_mission_definition/default_turtlebot.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/predefined_missions/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/predefined_missions/default.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/config/predefined_missions/default_turtlebot.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/eventhandlers/eventhandler.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/mission_planner/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/mission_planner/local_planner.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/mission_planner/mission_planner_interface.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/mission_planner/sequential_task_selector.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/mission_planner/task_selector_interface.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/models/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/modules.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/robot/robot.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/robot/robot_start_mission.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/robot/robot_status.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/robot/robot_stop_mission.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/robot/robot_task_status.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/script.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/auth/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/auth/azure_credentials.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/service_connections/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/service_connections/mqtt/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/service_connections/mqtt/robot_info_publisher.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/service_connections/request_handler.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/utilities/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/utilities/robot_utilities.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/services/utilities/threaded_request.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/await_next_mission.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/blocked_protective_stop.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/home.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/intervention_needed.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/offline.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/paused.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/recharging.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/robot_standing_still.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states/unknown_status.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/states_enum.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/functions/fail_mission.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/functions/finish_mission.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/functions/return_home.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/functions/robot_status.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/functions/utils.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/state_machine/transitions/robot_status.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/storage/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar/storage/utilities.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar.egg-info/SOURCES.txt +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar.egg-info/dependency_links.txt +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar.egg-info/entry_points.txt +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar.egg-info/requires.txt +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/isar.egg-info/top_level.txt +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/exceptions/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/exceptions/robot_exceptions.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/initialize/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/inspection/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/inspection/inspection.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/mission/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/mission/mission.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/mission/status.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/mission/task.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/robots/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/robots/battery_state.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/robots/media.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/models/robots/robot_model.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/robot_interface.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/telemetry/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/test_robot_interface.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/utilities/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/src/robot_interface/utilities/uuid_string_factory.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/conftest.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/integration/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/integration/turtlebot/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/integration/turtlebot/config/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/integration/turtlebot/config/maps/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/integration/turtlebot/config/maps/turtleworld.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/integration/turtlebot/config/missions/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/integration/turtlebot/config/missions/default.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/integration/turtlebot/test_successful_mission.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/apis/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/apis/models/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/apis/models/example_mission_definition.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/apis/models/test_start_mission_definition.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/apis/scheduler/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/apis/scheduler/test_scheduler_router.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/apis/security/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/apis/security/test_authentication.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/mission/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/mission/test_mission.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/models/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/models/communication/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/services/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/services/readers/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/services/readers/test_mission_reader.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/services/service_connections/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/services/service_connections/echo/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/services/service_connections/test_base_request_handler.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/services/utilities/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/state_machine/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/state_machine/states/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/state_machine/states/test_monitor.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/storage/test_blob_storage.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/isar/storage/test_uploader.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_data/test_map_config/test_map_config.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_data/test_mission_not_working.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_data/test_mission_working.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_data/test_mission_working_no_tasks.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_data/test_thermal_image_mission.json +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_double/__init__.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_double/blob_storage.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_double/mission_definition.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_double/pose.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_double/request.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_double/robot_interface.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_double/status.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_double/task.py +0 -0
- {isar-1.33.0 → isar-1.33.2}/tests/test_double/token.py +0 -0
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import logging
|
|
2
2
|
from http import HTTPStatus
|
|
3
|
-
from threading import Lock
|
|
4
3
|
|
|
5
4
|
from fastapi import Body, HTTPException, Path
|
|
6
5
|
|
|
@@ -29,7 +28,6 @@ class SchedulingController:
|
|
|
29
28
|
):
|
|
30
29
|
self.scheduling_utilities: SchedulingUtilities = scheduling_utilities
|
|
31
30
|
self.logger = logging.getLogger("api")
|
|
32
|
-
self.start_mission_lock: Lock = Lock()
|
|
33
31
|
|
|
34
32
|
def start_mission_by_id(
|
|
35
33
|
self,
|
|
@@ -77,67 +75,38 @@ class SchedulingController:
|
|
|
77
75
|
detail=error_message_no_mission_definition,
|
|
78
76
|
)
|
|
79
77
|
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
"Conflict - Another mission is currently being started"
|
|
83
|
-
)
|
|
84
|
-
self.logger.warning(error_message_another_mission_starting)
|
|
85
|
-
raise HTTPException(
|
|
86
|
-
status_code=HTTPStatus.CONFLICT,
|
|
87
|
-
detail=error_message_another_mission_starting,
|
|
88
|
-
)
|
|
78
|
+
state: States = self.scheduling_utilities.get_state()
|
|
79
|
+
self.scheduling_utilities.verify_state_machine_ready_to_receive_mission(state)
|
|
89
80
|
|
|
90
81
|
try:
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
state
|
|
82
|
+
mission: Mission = to_isar_mission(
|
|
83
|
+
start_mission_definition=mission_definition
|
|
94
84
|
)
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
error_message = f"Bad Request - Cannot create ISAR mission: {e}"
|
|
102
|
-
self.logger.warning(error_message)
|
|
103
|
-
raise HTTPException(
|
|
104
|
-
status_code=HTTPStatus.BAD_REQUEST,
|
|
105
|
-
detail=error_message,
|
|
106
|
-
)
|
|
107
|
-
|
|
108
|
-
self.scheduling_utilities.verify_robot_capable_of_mission(
|
|
109
|
-
mission=mission, robot_capabilities=robot_settings.CAPABILITIES
|
|
85
|
+
except MissionPlannerError as e:
|
|
86
|
+
error_message = f"Bad Request - Cannot create ISAR mission: {e}"
|
|
87
|
+
self.logger.warning(error_message)
|
|
88
|
+
raise HTTPException(
|
|
89
|
+
status_code=HTTPStatus.BAD_REQUEST,
|
|
90
|
+
detail=error_message,
|
|
110
91
|
)
|
|
111
92
|
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
93
|
+
self.scheduling_utilities.verify_robot_capable_of_mission(
|
|
94
|
+
mission=mission, robot_capabilities=robot_settings.CAPABILITIES
|
|
95
|
+
)
|
|
115
96
|
|
|
116
|
-
|
|
117
|
-
|
|
97
|
+
self.logger.info("Starting mission: %s", mission.id)
|
|
98
|
+
self.scheduling_utilities.start_mission(mission=mission)
|
|
99
|
+
return self._api_response(mission)
|
|
118
100
|
|
|
119
101
|
def return_home(self) -> None:
|
|
120
102
|
self.logger.info("Received request to return home")
|
|
121
103
|
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
self.logger.warning(error_message_another_mission_starting)
|
|
127
|
-
raise HTTPException(
|
|
128
|
-
status_code=HTTPStatus.CONFLICT,
|
|
129
|
-
detail=error_message_another_mission_starting,
|
|
130
|
-
)
|
|
131
|
-
|
|
132
|
-
try:
|
|
133
|
-
state: States = self.scheduling_utilities.get_state()
|
|
134
|
-
self.scheduling_utilities.verify_state_machine_ready_to_receive_return_home_mission(
|
|
135
|
-
state
|
|
136
|
-
)
|
|
104
|
+
state: States = self.scheduling_utilities.get_state()
|
|
105
|
+
self.scheduling_utilities.verify_state_machine_ready_to_receive_return_home_mission(
|
|
106
|
+
state
|
|
107
|
+
)
|
|
137
108
|
|
|
138
|
-
|
|
139
|
-
finally:
|
|
140
|
-
self.start_mission_lock.release()
|
|
109
|
+
self.scheduling_utilities.return_home()
|
|
141
110
|
|
|
142
111
|
def pause_mission(self) -> ControlMissionResponse:
|
|
143
112
|
self.logger.info("Received request to pause current mission")
|
|
@@ -244,6 +244,11 @@ class Settings(BaseSettings):
|
|
|
244
244
|
default="intervention_needed", validate_default=True
|
|
245
245
|
)
|
|
246
246
|
|
|
247
|
+
# List of MQTT Topics Expiry
|
|
248
|
+
MQTT_ROBOT_HEARTBEAT_EXPIRY: int = Field(default=5)
|
|
249
|
+
MQTT_TELEMETRY_EXPIRY: int = Field(default=10)
|
|
250
|
+
MQTT_MISSION_AND_TASK_EXPIRY: int = Field(default=86400)
|
|
251
|
+
|
|
247
252
|
# Logging
|
|
248
253
|
|
|
249
254
|
# Log handlers
|
|
@@ -17,12 +17,15 @@ T2 = TypeVar("T2")
|
|
|
17
17
|
|
|
18
18
|
|
|
19
19
|
class Event(Queue[T]):
|
|
20
|
-
def __init__(self) -> None:
|
|
20
|
+
def __init__(self, name: str) -> None:
|
|
21
21
|
super().__init__(maxsize=1)
|
|
22
|
+
self.name = name
|
|
22
23
|
|
|
23
24
|
def trigger_event(self, data: T, timeout: int = None) -> None:
|
|
24
25
|
try:
|
|
25
|
-
|
|
26
|
+
# We always want a timeout when blocking for results, so that
|
|
27
|
+
# the thread will never get stuck waiting for a result
|
|
28
|
+
self.put(data, block=timeout is not None, timeout=timeout)
|
|
26
29
|
except Exception:
|
|
27
30
|
if timeout is not None:
|
|
28
31
|
raise EventTimeoutError
|
|
@@ -79,46 +82,62 @@ class APIEvent(Generic[T1, T2]):
|
|
|
79
82
|
api to state machine while the response is from state machine to api.
|
|
80
83
|
"""
|
|
81
84
|
|
|
82
|
-
def __init__(self):
|
|
83
|
-
self.request: Event[T1] = Event()
|
|
84
|
-
self.response: Event[T2] = Event()
|
|
85
|
+
def __init__(self, name: str):
|
|
86
|
+
self.request: Event[T1] = Event("api-" + name + "-request")
|
|
87
|
+
self.response: Event[T2] = Event("api-" + name + "-request")
|
|
85
88
|
|
|
86
89
|
|
|
87
90
|
class APIRequests:
|
|
88
91
|
def __init__(self) -> None:
|
|
89
|
-
self.start_mission: APIEvent[Mission, MissionStartResponse] = APIEvent(
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
self.
|
|
93
|
-
|
|
94
|
-
|
|
92
|
+
self.start_mission: APIEvent[Mission, MissionStartResponse] = APIEvent(
|
|
93
|
+
"start_mission"
|
|
94
|
+
)
|
|
95
|
+
self.stop_mission: APIEvent[str, ControlMissionResponse] = APIEvent(
|
|
96
|
+
"stop_mission"
|
|
97
|
+
)
|
|
98
|
+
self.pause_mission: APIEvent[bool, ControlMissionResponse] = APIEvent(
|
|
99
|
+
"pause_mission"
|
|
100
|
+
)
|
|
101
|
+
self.resume_mission: APIEvent[bool, ControlMissionResponse] = APIEvent(
|
|
102
|
+
"resume_mission"
|
|
103
|
+
)
|
|
104
|
+
self.return_home: APIEvent[bool, bool] = APIEvent("return_home")
|
|
105
|
+
self.release_intervention_needed: APIEvent[bool, bool] = APIEvent(
|
|
106
|
+
"release_intervention_needed"
|
|
107
|
+
)
|
|
95
108
|
|
|
96
109
|
|
|
97
110
|
class StateMachineEvents:
|
|
98
111
|
def __init__(self) -> None:
|
|
99
|
-
self.start_mission: Event[Mission] = Event()
|
|
100
|
-
self.stop_mission: Event[bool] = Event()
|
|
101
|
-
self.pause_mission: Event[bool] = Event()
|
|
102
|
-
self.task_status_request: Event[str] = Event()
|
|
112
|
+
self.start_mission: Event[Mission] = Event("start_mission")
|
|
113
|
+
self.stop_mission: Event[bool] = Event("stop_mission")
|
|
114
|
+
self.pause_mission: Event[bool] = Event("pause_mission")
|
|
115
|
+
self.task_status_request: Event[str] = Event("task_status_request")
|
|
103
116
|
|
|
104
117
|
|
|
105
118
|
class RobotServiceEvents:
|
|
106
119
|
def __init__(self) -> None:
|
|
107
|
-
self.task_status_updated: Event[TaskStatus] = Event()
|
|
108
|
-
self.task_status_failed: Event[ErrorMessage] = Event()
|
|
109
|
-
self.mission_started: Event[bool] = Event()
|
|
110
|
-
self.mission_failed: Event[ErrorMessage] = Event()
|
|
111
|
-
self.robot_status_changed: Event[bool] = Event()
|
|
112
|
-
self.mission_failed_to_stop: Event[ErrorMessage] = Event(
|
|
113
|
-
|
|
120
|
+
self.task_status_updated: Event[TaskStatus] = Event("task_status_updated")
|
|
121
|
+
self.task_status_failed: Event[ErrorMessage] = Event("task_status_failed")
|
|
122
|
+
self.mission_started: Event[bool] = Event("mission_started")
|
|
123
|
+
self.mission_failed: Event[ErrorMessage] = Event("mission_failed")
|
|
124
|
+
self.robot_status_changed: Event[bool] = Event("robot_status_changed")
|
|
125
|
+
self.mission_failed_to_stop: Event[ErrorMessage] = Event(
|
|
126
|
+
"mission_failed_to_stop"
|
|
127
|
+
)
|
|
128
|
+
self.mission_successfully_stopped: Event[bool] = Event(
|
|
129
|
+
"mission_successfully_stopped"
|
|
130
|
+
)
|
|
114
131
|
|
|
115
132
|
|
|
116
133
|
class SharedState:
|
|
117
134
|
def __init__(self) -> None:
|
|
118
|
-
self.state: Event[State] = Event()
|
|
119
|
-
self.robot_status: Event[RobotStatus] = Event()
|
|
120
|
-
self.state_machine_current_task: Event[TASKS] = Event(
|
|
121
|
-
|
|
135
|
+
self.state: Event[State] = Event("state")
|
|
136
|
+
self.robot_status: Event[RobotStatus] = Event("robot_status")
|
|
137
|
+
self.state_machine_current_task: Event[TASKS] = Event(
|
|
138
|
+
"state_machine_current_task"
|
|
139
|
+
)
|
|
140
|
+
self.robot_battery_level: Event[float] = Event("robot_battery_level")
|
|
122
141
|
|
|
123
142
|
|
|
124
143
|
class EventTimeoutError(Exception):
|
|
@@ -1,15 +1,24 @@
|
|
|
1
1
|
import logging
|
|
2
2
|
import os
|
|
3
|
+
import time
|
|
3
4
|
from queue import Empty, Queue
|
|
4
5
|
|
|
5
6
|
import backoff
|
|
6
7
|
from paho.mqtt import client as mqtt
|
|
7
8
|
from paho.mqtt.client import Client
|
|
9
|
+
from paho.mqtt.packettypes import PacketTypes
|
|
10
|
+
from paho.mqtt.properties import Properties
|
|
8
11
|
|
|
9
12
|
from isar.config.settings import settings
|
|
10
13
|
from robot_interface.telemetry.mqtt_client import MqttClientInterface
|
|
11
14
|
|
|
12
15
|
|
|
16
|
+
def props_expiry(seconds: int) -> Properties:
|
|
17
|
+
p = Properties(PacketTypes.PUBLISH)
|
|
18
|
+
p.MessageExpiryInterval = seconds
|
|
19
|
+
return p
|
|
20
|
+
|
|
21
|
+
|
|
13
22
|
def _on_success(data: dict) -> None:
|
|
14
23
|
logging.getLogger("mqtt_client").info("Connected to MQTT Broker")
|
|
15
24
|
logging.getLogger("mqtt_client").debug(
|
|
@@ -53,7 +62,9 @@ class MqttClient(MqttClientInterface):
|
|
|
53
62
|
|
|
54
63
|
self.port: int = settings.MQTT_PORT
|
|
55
64
|
|
|
56
|
-
self.client: Client = Client(
|
|
65
|
+
self.client: Client = Client(
|
|
66
|
+
protocol=mqtt.MQTTv5, callback_api_version=mqtt.CallbackAPIVersion.VERSION2
|
|
67
|
+
)
|
|
57
68
|
|
|
58
69
|
self.client.enable_logger(logger=self.logger)
|
|
59
70
|
|
|
@@ -74,20 +85,36 @@ class MqttClient(MqttClientInterface):
|
|
|
74
85
|
|
|
75
86
|
while True:
|
|
76
87
|
if not self.client.is_connected():
|
|
88
|
+
time.sleep(0) # avoid CPU spin
|
|
77
89
|
continue
|
|
78
90
|
try:
|
|
79
|
-
|
|
91
|
+
item = self.mqtt_queue.get(timeout=1)
|
|
92
|
+
if len(item) == 4:
|
|
93
|
+
topic, payload, qos, retain = item
|
|
94
|
+
properties = None
|
|
95
|
+
else:
|
|
96
|
+
topic, payload, qos, retain, properties = item
|
|
80
97
|
except Empty:
|
|
81
98
|
continue
|
|
82
99
|
|
|
83
|
-
self.publish(
|
|
100
|
+
self.publish(
|
|
101
|
+
topic=topic,
|
|
102
|
+
payload=payload,
|
|
103
|
+
qos=qos,
|
|
104
|
+
retain=retain,
|
|
105
|
+
properties=properties,
|
|
106
|
+
)
|
|
84
107
|
|
|
85
|
-
def on_connect(self, client, userdata, flags,
|
|
86
|
-
self.logger.info(
|
|
108
|
+
def on_connect(self, client, userdata, flags, reason_code, properties):
|
|
109
|
+
self.logger.info(
|
|
110
|
+
"Connection returned result: " + mqtt.connack_string(reason_code)
|
|
111
|
+
)
|
|
87
112
|
|
|
88
|
-
def on_disconnect(self, client, userdata,
|
|
89
|
-
if
|
|
90
|
-
self.logger.warning(
|
|
113
|
+
def on_disconnect(self, client, userdata, reason_code, properties):
|
|
114
|
+
if reason_code != 0:
|
|
115
|
+
self.logger.warning(
|
|
116
|
+
f"Unexpected disconnection from MQTT Broker, {reason_code}"
|
|
117
|
+
)
|
|
91
118
|
|
|
92
119
|
@backoff.on_exception(
|
|
93
120
|
backoff.expo,
|
|
@@ -102,6 +129,15 @@ class MqttClient(MqttClientInterface):
|
|
|
102
129
|
self.logger.info("Host: %s, Port: %s", host, port)
|
|
103
130
|
self.client.connect(host=host, port=port)
|
|
104
131
|
|
|
105
|
-
def publish(
|
|
132
|
+
def publish(
|
|
133
|
+
self,
|
|
134
|
+
topic: str,
|
|
135
|
+
payload: str,
|
|
136
|
+
qos: int = 0,
|
|
137
|
+
retain: bool = False,
|
|
138
|
+
properties=None,
|
|
139
|
+
):
|
|
106
140
|
self.logger.debug("Publishing message to topic: %s", topic)
|
|
107
|
-
self.client.publish(
|
|
141
|
+
self.client.publish(
|
|
142
|
+
topic=topic, payload=payload, qos=qos, retain=retain, properties=properties
|
|
143
|
+
)
|
{isar-1.33.0 → isar-1.33.2}/src/isar/services/service_connections/mqtt/robot_heartbeat_publisher.py
RENAMED
|
@@ -4,6 +4,7 @@ from datetime import datetime, timezone
|
|
|
4
4
|
from queue import Queue
|
|
5
5
|
|
|
6
6
|
from isar.config.settings import settings
|
|
7
|
+
from isar.services.service_connections.mqtt.mqtt_client import props_expiry
|
|
7
8
|
from robot_interface.telemetry.mqtt_client import MqttPublisher
|
|
8
9
|
from robot_interface.telemetry.payloads import RobotHeartbeatPayload
|
|
9
10
|
from robot_interface.utilities.json_service import EnhancedJSONEncoder
|
|
@@ -24,6 +25,8 @@ class RobotHeartbeatPublisher:
|
|
|
24
25
|
self.mqtt_publisher.publish(
|
|
25
26
|
topic=settings.TOPIC_ISAR_ROBOT_HEARTBEAT,
|
|
26
27
|
payload=json.dumps(payload, cls=EnhancedJSONEncoder),
|
|
28
|
+
retain=True,
|
|
29
|
+
properties=props_expiry(settings.MQTT_ROBOT_HEARTBEAT_EXPIRY),
|
|
27
30
|
)
|
|
28
31
|
|
|
29
32
|
time.sleep(settings.ROBOT_HEARTBEAT_PUBLISH_INTERVAL)
|
|
@@ -15,6 +15,7 @@ from isar.mission_planner.task_selector_interface import (
|
|
|
15
15
|
TaskSelectorStop,
|
|
16
16
|
)
|
|
17
17
|
from isar.models.events import Events, SharedState
|
|
18
|
+
from isar.services.service_connections.mqtt.mqtt_client import props_expiry
|
|
18
19
|
from isar.state_machine.states.await_next_mission import AwaitNextMission
|
|
19
20
|
from isar.state_machine.states.blocked_protective_stop import BlockedProtectiveStop
|
|
20
21
|
from isar.state_machine.states.home import Home
|
|
@@ -285,10 +286,11 @@ class StateMachine(object):
|
|
|
285
286
|
)
|
|
286
287
|
|
|
287
288
|
self.mqtt_publisher.publish(
|
|
288
|
-
topic=settings.TOPIC_ISAR_MISSION,
|
|
289
|
+
topic=settings.TOPIC_ISAR_MISSION + f"/{self.current_mission.id}",
|
|
289
290
|
payload=json.dumps(payload, cls=EnhancedJSONEncoder),
|
|
290
291
|
qos=1,
|
|
291
292
|
retain=True,
|
|
293
|
+
properties=props_expiry(settings.MQTT_MISSION_AND_TASK_EXPIRY),
|
|
292
294
|
)
|
|
293
295
|
|
|
294
296
|
def publish_task_status(self, task: TASKS) -> None:
|
|
@@ -316,10 +318,11 @@ class StateMachine(object):
|
|
|
316
318
|
)
|
|
317
319
|
|
|
318
320
|
self.mqtt_publisher.publish(
|
|
319
|
-
topic=settings.TOPIC_ISAR_TASK,
|
|
321
|
+
topic=settings.TOPIC_ISAR_TASK + f"/{task.id}",
|
|
320
322
|
payload=json.dumps(payload, cls=EnhancedJSONEncoder),
|
|
321
323
|
qos=1,
|
|
322
324
|
retain=True,
|
|
325
|
+
properties=props_expiry(settings.MQTT_MISSION_AND_TASK_EXPIRY),
|
|
323
326
|
)
|
|
324
327
|
|
|
325
328
|
def publish_intervention_needed(self, error_message: str) -> None:
|
|
@@ -406,7 +409,7 @@ class StateMachine(object):
|
|
|
406
409
|
)
|
|
407
410
|
|
|
408
411
|
def _queue_empty_response(self) -> None:
|
|
409
|
-
self.events.api_requests.stop_mission.response.
|
|
412
|
+
self.events.api_requests.stop_mission.response.trigger_event(
|
|
410
413
|
ControlMissionResponse(
|
|
411
414
|
mission_id="None",
|
|
412
415
|
mission_status="None",
|
|
@@ -60,9 +60,7 @@ class Monitor(EventHandlerBase):
|
|
|
60
60
|
state_machine.logger.warning(
|
|
61
61
|
"Cancelling current mission due to low battery"
|
|
62
62
|
)
|
|
63
|
-
state_machine.
|
|
64
|
-
state_machine.current_task = None
|
|
65
|
-
return state_machine.request_return_home # type: ignore
|
|
63
|
+
return state_machine.stop # type: ignore
|
|
66
64
|
return None
|
|
67
65
|
|
|
68
66
|
event_handlers: List[EventHandlerMapping] = [
|
|
@@ -2,7 +2,7 @@ from typing import TYPE_CHECKING, Callable, List, Optional
|
|
|
2
2
|
|
|
3
3
|
from isar.apis.models.models import MissionStartResponse
|
|
4
4
|
from isar.eventhandlers.eventhandler import EventHandlerBase, EventHandlerMapping
|
|
5
|
-
from isar.models.events import Event
|
|
5
|
+
from isar.models.events import Event
|
|
6
6
|
from isar.state_machine.utils.common_event_handlers import (
|
|
7
7
|
mission_failed_event_handler,
|
|
8
8
|
mission_started_event_handler,
|
|
@@ -43,17 +43,14 @@ class ReturningHome(EventHandlerBase):
|
|
|
43
43
|
) -> Optional[Callable]:
|
|
44
44
|
if event.has_event():
|
|
45
45
|
if not state_machine.battery_level_is_above_mission_start_threshold():
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
)
|
|
55
|
-
except EventTimeoutError:
|
|
56
|
-
pass
|
|
46
|
+
response = MissionStartResponse(
|
|
47
|
+
mission_id=None,
|
|
48
|
+
mission_started=False,
|
|
49
|
+
mission_not_started_reason="Robot battery too low",
|
|
50
|
+
)
|
|
51
|
+
state_machine.events.api_requests.start_mission.response.trigger_event(
|
|
52
|
+
response
|
|
53
|
+
)
|
|
57
54
|
return None
|
|
58
55
|
return state_machine.stop # type: ignore
|
|
59
56
|
return None
|
|
@@ -1,9 +1,11 @@
|
|
|
1
1
|
import logging
|
|
2
2
|
from typing import TYPE_CHECKING, Callable, List, Optional
|
|
3
3
|
|
|
4
|
+
from isar.apis.models.models import ControlMissionResponse
|
|
4
5
|
from isar.eventhandlers.eventhandler import EventHandlerBase, EventHandlerMapping
|
|
5
6
|
from isar.models.events import Event
|
|
6
7
|
from robot_interface.models.exceptions.robot_exceptions import ErrorMessage
|
|
8
|
+
from robot_interface.models.mission.status import MissionStatus, TaskStatus
|
|
7
9
|
|
|
8
10
|
if TYPE_CHECKING:
|
|
9
11
|
from isar.state_machine.state_machine import StateMachine
|
|
@@ -15,6 +17,32 @@ class Stopping(EventHandlerBase):
|
|
|
15
17
|
logger = logging.getLogger("state_machine")
|
|
16
18
|
events = state_machine.events
|
|
17
19
|
|
|
20
|
+
def _stop_mission_cleanup() -> None:
|
|
21
|
+
if state_machine.current_mission is None:
|
|
22
|
+
state_machine._queue_empty_response()
|
|
23
|
+
state_machine.reset_state_machine()
|
|
24
|
+
return None
|
|
25
|
+
|
|
26
|
+
state_machine.current_mission.status = MissionStatus.Cancelled
|
|
27
|
+
|
|
28
|
+
for task in state_machine.current_mission.tasks:
|
|
29
|
+
if task.status in [
|
|
30
|
+
TaskStatus.NotStarted,
|
|
31
|
+
TaskStatus.InProgress,
|
|
32
|
+
TaskStatus.Paused,
|
|
33
|
+
]:
|
|
34
|
+
task.status = TaskStatus.Cancelled
|
|
35
|
+
|
|
36
|
+
stopped_mission_response: ControlMissionResponse = (
|
|
37
|
+
state_machine._make_control_mission_response()
|
|
38
|
+
)
|
|
39
|
+
state_machine.events.api_requests.stop_mission.response.trigger_event(
|
|
40
|
+
stopped_mission_response
|
|
41
|
+
)
|
|
42
|
+
state_machine.publish_task_status(task=state_machine.current_task)
|
|
43
|
+
state_machine._finalize()
|
|
44
|
+
return None
|
|
45
|
+
|
|
18
46
|
def _failed_stop_event_handler(
|
|
19
47
|
event: Event[ErrorMessage],
|
|
20
48
|
) -> Optional[Callable]:
|
|
@@ -38,6 +66,11 @@ class Stopping(EventHandlerBase):
|
|
|
38
66
|
):
|
|
39
67
|
return state_machine.return_home_mission_stopped # type: ignore
|
|
40
68
|
else:
|
|
69
|
+
_stop_mission_cleanup()
|
|
70
|
+
if (
|
|
71
|
+
not state_machine.battery_level_is_above_mission_start_threshold()
|
|
72
|
+
):
|
|
73
|
+
return state_machine.request_return_home # type: ignore
|
|
41
74
|
return state_machine.mission_stopped # type: ignore
|
|
42
75
|
return None
|
|
43
76
|
|
|
@@ -29,7 +29,7 @@ def pause_mission(state_machine: "StateMachine") -> bool:
|
|
|
29
29
|
paused_mission_response: ControlMissionResponse = (
|
|
30
30
|
state_machine._make_control_mission_response()
|
|
31
31
|
)
|
|
32
|
-
state_machine.events.api_requests.pause_mission.response.
|
|
32
|
+
state_machine.events.api_requests.pause_mission.response.trigger_event(
|
|
33
33
|
paused_mission_response
|
|
34
34
|
)
|
|
35
35
|
|
|
@@ -35,7 +35,7 @@ def resume_mission(state_machine: "StateMachine") -> bool:
|
|
|
35
35
|
resume_mission_response: ControlMissionResponse = (
|
|
36
36
|
state_machine._make_control_mission_response()
|
|
37
37
|
)
|
|
38
|
-
state_machine.events.api_requests.resume_mission.response.
|
|
38
|
+
state_machine.events.api_requests.resume_mission.response.trigger_event(
|
|
39
39
|
resume_mission_response
|
|
40
40
|
)
|
|
41
41
|
|
|
@@ -13,7 +13,7 @@ from robot_interface.models.mission.status import MissionStatus, TaskStatus
|
|
|
13
13
|
|
|
14
14
|
|
|
15
15
|
def acknowledge_mission(state_machine: "StateMachine") -> bool:
|
|
16
|
-
state_machine.events.api_requests.start_mission.response.
|
|
16
|
+
state_machine.events.api_requests.start_mission.response.trigger_event(
|
|
17
17
|
MissionStartResponse(mission_started=True)
|
|
18
18
|
)
|
|
19
19
|
return True
|
|
@@ -66,14 +66,14 @@ def set_mission_to_in_progress(state_machine: "StateMachine") -> bool:
|
|
|
66
66
|
|
|
67
67
|
|
|
68
68
|
def trigger_start_mission_event(state_machine: "StateMachine") -> bool:
|
|
69
|
-
state_machine.events.state_machine_events.start_mission.
|
|
69
|
+
state_machine.events.state_machine_events.start_mission.trigger_event(
|
|
70
70
|
state_machine.current_mission
|
|
71
71
|
)
|
|
72
72
|
return True
|
|
73
73
|
|
|
74
74
|
|
|
75
75
|
def _initialization_failed(state_machine: "StateMachine") -> None:
|
|
76
|
-
state_machine.events.api_requests.start_mission.response.
|
|
76
|
+
state_machine.events.api_requests.start_mission.response.trigger_event(
|
|
77
77
|
MissionStartResponse(
|
|
78
78
|
mission_started=False,
|
|
79
79
|
mission_not_started_reason="Failed to initialize robot",
|
|
@@ -12,38 +12,11 @@ def trigger_stop_mission_event(state_machine: "StateMachine") -> bool:
|
|
|
12
12
|
return True
|
|
13
13
|
|
|
14
14
|
|
|
15
|
-
def stop_mission_cleanup(state_machine: "StateMachine") -> bool:
|
|
16
|
-
if state_machine.current_mission is None:
|
|
17
|
-
state_machine._queue_empty_response()
|
|
18
|
-
state_machine.reset_state_machine()
|
|
19
|
-
return True
|
|
20
|
-
|
|
21
|
-
state_machine.current_mission.status = MissionStatus.Cancelled
|
|
22
|
-
|
|
23
|
-
for task in state_machine.current_mission.tasks:
|
|
24
|
-
if task.status in [
|
|
25
|
-
TaskStatus.NotStarted,
|
|
26
|
-
TaskStatus.InProgress,
|
|
27
|
-
TaskStatus.Paused,
|
|
28
|
-
]:
|
|
29
|
-
task.status = TaskStatus.Cancelled
|
|
30
|
-
|
|
31
|
-
stopped_mission_response: ControlMissionResponse = (
|
|
32
|
-
state_machine._make_control_mission_response()
|
|
33
|
-
)
|
|
34
|
-
state_machine.events.api_requests.stop_mission.response.put(
|
|
35
|
-
stopped_mission_response
|
|
36
|
-
)
|
|
37
|
-
state_machine.publish_task_status(task=state_machine.current_task)
|
|
38
|
-
state_machine._finalize()
|
|
39
|
-
return True
|
|
40
|
-
|
|
41
|
-
|
|
42
15
|
def stop_mission_failed(state_machine: "StateMachine") -> bool:
|
|
43
16
|
stopped_mission_response: ControlMissionResponse = (
|
|
44
17
|
state_machine._make_control_mission_response()
|
|
45
18
|
)
|
|
46
|
-
state_machine.events.api_requests.stop_mission.response.
|
|
19
|
+
state_machine.events.api_requests.stop_mission.response.trigger_event(
|
|
47
20
|
stopped_mission_response
|
|
48
21
|
)
|
|
49
22
|
return True
|
|
@@ -69,7 +42,7 @@ def stop_return_home_mission_cleanup(state_machine: "StateMachine") -> bool:
|
|
|
69
42
|
stopped_mission_response: ControlMissionResponse = (
|
|
70
43
|
state_machine._make_control_mission_response()
|
|
71
44
|
)
|
|
72
|
-
state_machine.events.api_requests.stop_mission.response.
|
|
45
|
+
state_machine.events.api_requests.stop_mission.response.trigger_event(
|
|
73
46
|
stopped_mission_response
|
|
74
47
|
)
|
|
75
48
|
|
|
@@ -83,7 +56,7 @@ def stop_return_home_mission_failed(state_machine: "StateMachine") -> bool:
|
|
|
83
56
|
stopped_mission_response: ControlMissionResponse = (
|
|
84
57
|
state_machine._make_control_mission_response()
|
|
85
58
|
)
|
|
86
|
-
state_machine.events.api_requests.stop_mission.response.
|
|
59
|
+
state_machine.events.api_requests.stop_mission.response.trigger_event(
|
|
87
60
|
stopped_mission_response
|
|
88
61
|
)
|
|
89
62
|
return True
|
|
@@ -14,7 +14,6 @@ from isar.state_machine.transitions.functions.start_mission import (
|
|
|
14
14
|
trigger_start_mission_event,
|
|
15
15
|
)
|
|
16
16
|
from isar.state_machine.transitions.functions.stop import (
|
|
17
|
-
stop_mission_cleanup,
|
|
18
17
|
stop_mission_failed,
|
|
19
18
|
stop_return_home_mission_cleanup,
|
|
20
19
|
stop_return_home_mission_failed,
|
|
@@ -66,7 +65,6 @@ def get_mission_transitions(state_machine: "StateMachine") -> List[dict]:
|
|
|
66
65
|
"trigger": "mission_stopped",
|
|
67
66
|
"source": state_machine.stopping_state,
|
|
68
67
|
"dest": state_machine.await_next_mission_state,
|
|
69
|
-
"before": def_transition(state_machine, stop_mission_cleanup),
|
|
70
68
|
},
|
|
71
69
|
{
|
|
72
70
|
"trigger": "mission_stopping_failed",
|
|
@@ -31,13 +31,13 @@ def get_return_home_transitions(state_machine: "StateMachine") -> List[dict]:
|
|
|
31
31
|
state_machine.robot_standing_still_state,
|
|
32
32
|
state_machine.intervention_needed_state,
|
|
33
33
|
state_machine.monitor_state,
|
|
34
|
+
state_machine.stopping_state,
|
|
34
35
|
],
|
|
35
36
|
"dest": state_machine.returning_home_state,
|
|
36
37
|
"conditions": [
|
|
37
38
|
def_transition(state_machine, start_return_home_mission),
|
|
38
39
|
def_transition(state_machine, set_return_home_status),
|
|
39
40
|
def_transition(state_machine, initialize_robot),
|
|
40
|
-
def_transition(state_machine, initialize_robot),
|
|
41
41
|
],
|
|
42
42
|
"before": def_transition(state_machine, trigger_start_mission_event),
|
|
43
43
|
},
|