-
Notifications
You must be signed in to change notification settings - Fork 0
355 navigation loss of gps signal or weak gps signal #396
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from all commits
e00cb48
5988bb1
e899c9b
87d802e
e45eb95
a0715af
d990f8e
2607d21
c2c96bb
c9c1c51
75cf059
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,25 @@ | ||
| # SPDX-FileCopyrightText: Alliander N. V. | ||
| # | ||
| # SPDX-License-Identifier: Apache-2.0 | ||
| ARG BASE_IMAGE=ubuntu:latest | ||
| FROM $BASE_IMAGE | ||
|
|
||
| ARG COLCON_BUILD_SEQUENTIAL | ||
| ENV ROS_DISTRO=jazzy | ||
|
|
||
| # Install repo packages: | ||
| WORKDIR /$WORKDIR/ros | ||
| COPY alliander_core/src/ /$WORKDIR/ros/src | ||
| COPY alliander_diagnostics/src/ /$WORKDIR/ros/src | ||
| RUN /$WORKDIR/colcon_build.sh | ||
|
|
||
| # Install python dependencies: | ||
| WORKDIR $WORKDIR | ||
| COPY pyproject.toml /$WORKDIR/pyproject.toml | ||
| RUN uv sync \ | ||
| && echo "export PYTHONPATH=\"$(dirname $(dirname $(uv python find)))/lib/python3.12/site-packages:\$PYTHONPATH\"" >> /root/.bashrc \ | ||
| && echo "export PATH=\"$(dirname $(dirname $(uv python find)))/bin:\$PATH\"" >> /root/.bashrc | ||
|
|
||
| WORKDIR /$WORKDIR | ||
| ENTRYPOINT ["/entrypoint.sh"] | ||
| CMD ["sleep", "infinity"] |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,17 @@ | ||
| # SPDX-FileCopyrightText: Alliander N. V. | ||
| # | ||
| # SPDX-License-Identifier: Apache-2.0 | ||
| services: | ||
| alliander_diagnostics: | ||
| image: allianderrobotics/diagnostics | ||
| container_name: alliander_diagnostics | ||
| network_mode: host | ||
| privileged: true | ||
| mem_limit: 6gb | ||
| tty: true | ||
| volumes: | ||
| - "/tmp/.X11-unix:/tmp/.X11-unix" | ||
| - "/dev:/dev" | ||
| env_file: | ||
| - .env | ||
| command: ["/bin/bash", "-c", "ros2 launch alliander_diagnostics diagnostics.launch.py"] |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,48 @@ | ||
| # SPDX-FileCopyrightText: Alliander N. V. | ||
| # | ||
| # SPDX-License-Identifier: Apache-2.0 | ||
|
|
||
| cmake_minimum_required(VERSION 3.5) | ||
| project(alliander_diagnostics) | ||
|
|
||
| # CMake dependencies: | ||
| find_package(ament_cmake REQUIRED) | ||
|
|
||
| # Other dependencies: | ||
| find_package(rclcpp REQUIRED) | ||
| find_package(diagnostic_msgs REQUIRED) | ||
| find_package(sensor_msgs REQUIRED) | ||
|
|
||
| # C++ executables: | ||
| include_directories(include) | ||
| add_executable(diagnostics | ||
| src/diagnostics_node.cpp | ||
| src/gps_diagnostics.cpp | ||
| ) | ||
| target_include_directories(diagnostics PUBLIC | ||
| $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/include> | ||
| $<INSTALL_INTERFACE:include>) | ||
| ament_target_dependencies(diagnostics | ||
| diagnostic_msgs | ||
| rclcpp | ||
| sensor_msgs | ||
| ) | ||
|
|
||
| install( | ||
| TARGETS diagnostics | ||
| DESTINATION lib/${PROJECT_NAME} | ||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Any specific reason for putting this executable in |
||
| ) | ||
|
|
||
| # Shared folders: | ||
| install( | ||
| DIRECTORY launch | ||
| DESTINATION share/${PROJECT_NAME} | ||
| ) | ||
|
|
||
| # Default test: | ||
| if(BUILD_TESTING) | ||
| find_package(ament_lint_auto REQUIRED) | ||
| ament_lint_auto_find_test_dependencies() | ||
| endif() | ||
|
|
||
| ament_package() | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,57 @@ | ||
| // # SPDX-FileCopyrightText: Alliander N. V. | ||
| // | ||
| // # SPDX-License-Identifier: Apache-2.0 | ||
|
|
||
| #ifndef BASE_DIAGNOSTICS_HPP_ | ||
| #define BASE_DIAGNOSTICS_HPP_ | ||
|
|
||
| #include <diagnostic_msgs/msg/diagnostic_status.hpp> | ||
| #include <mutex> | ||
| #include <rclcpp/rclcpp.hpp> | ||
|
|
||
| /** | ||
| * @brief Base class for diagnostic modules. | ||
| * | ||
| * This class provides a common interface for evaluating and reporting | ||
| * diagnostic status of a component. Derived classes implement the | ||
| * evaluate() function to update the diagnostic status based on | ||
| * monitored data. | ||
| */ | ||
| class BaseDiagnostics { | ||
| public: | ||
| /** | ||
| * @brief Construct a BaseDiagnostics instance. | ||
| * @param name Name of the diagnostic component. | ||
| * @param hardware_id Identifier of the associated hardware. | ||
| */ | ||
| BaseDiagnostics(const std::string& name, const std::string& hardware_id) { | ||
| status_.name = name; | ||
| status_.hardware_id = hardware_id; | ||
| } | ||
|
|
||
| virtual ~BaseDiagnostics() = default; | ||
|
|
||
| /** | ||
| * @brief Evaluate the monitored data and update the diagnostic status. | ||
| * @param now current time. | ||
| */ | ||
| virtual void evaluate(rclcpp::Time now) = 0; | ||
|
|
||
| /** | ||
| * @brief Get the current diagnostic status. | ||
| * @return Copy of the diagnostic status message. | ||
| */ | ||
| diagnostic_msgs::msg::DiagnosticStatus get_status() { | ||
| std::lock_guard<std::mutex> lock(mutex_); | ||
| return status_; | ||
| } | ||
|
|
||
| protected: | ||
| /// Current diagnostic status message. | ||
| diagnostic_msgs::msg::DiagnosticStatus status_; | ||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Perhaps the |
||
|
|
||
| /// Mutex protecting access to the status message. | ||
| std::mutex mutex_; | ||
| }; | ||
|
|
||
| #endif // BASE_DIAGNOSTICS_HPP_ | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,45 @@ | ||
| // # SPDX-FileCopyrightText: Alliander N. V. | ||
| // | ||
| // # SPDX-License-Identifier: Apache-2.0 | ||
|
|
||
| #ifndef DIAGNOSTICS_NODE_HPP_ | ||
| #define DIAGNOSTICS_NODE_HPP_ | ||
|
|
||
| #include <diagnostic_msgs/msg/diagnostic_array.hpp> | ||
| #include <rclcpp/rclcpp.hpp> | ||
|
|
||
| #include "base_diagnostics.hpp" | ||
|
|
||
| /** | ||
| * @brief Node responsible for collecting and publishing diagnostics. | ||
| * | ||
| * This class manages a set of diagnostic modules derived from | ||
| * BaseDiagnostics. It periodically evaluates each module and | ||
| * publishes the combined diagnostic status as a DiagnosticArray. | ||
| */ | ||
| class DiagnosticsNode { | ||
| public: | ||
| /** | ||
| * @brief Construct the diagnostics node. | ||
| * @param node The ROS2 node. | ||
| */ | ||
| DiagnosticsNode(rclcpp::Node::SharedPtr node); | ||
|
|
||
| private: | ||
| /// ROS2 node used for logging, parameters and communication. | ||
| rclcpp::Node::SharedPtr node_; | ||
| /// Publisher for the aggregated diagnostics message. | ||
| rclcpp::Publisher<diagnostic_msgs::msg::DiagnosticArray>::SharedPtr pub_diag; | ||
| /// Timer used to periodically trigger diagnostics evaluation. | ||
| rclcpp::TimerBase::SharedPtr timer; | ||
| /// Collection of diagnostic modules managed by this node. | ||
| std::vector<std::shared_ptr<BaseDiagnostics>> diagnostics_modules; | ||
|
|
||
| /** | ||
| * @brief Timer callback that evaluates all diagnostic modules | ||
| * and publishes the resulting diagnostic array. | ||
| */ | ||
| void diagnostics_cb(); | ||
| }; | ||
|
|
||
| #endif // DIAGNOSTICS_NODE_HPP_ |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,75 @@ | ||
| // # SPDX-FileCopyrightText: Alliander N. V. | ||
| // | ||
| // # SPDX-License-Identifier: Apache-2.0 | ||
|
|
||
| #ifndef GPS_DIAGNOSTICS_HPP_ | ||
| #define GPS_DIAGNOSTICS_HPP_ | ||
|
|
||
| #include <sensor_msgs/msg/nav_sat_fix.hpp> | ||
|
|
||
| #include "base_diagnostics.hpp" | ||
|
|
||
| /** | ||
| * @brief Diagnostic module for monitoring GPS health. | ||
| * | ||
| * This class subscribes to a NavSatFix topic and evaluates the | ||
| * quality and availability of the GPS signal. The diagnostic status | ||
| * is updated based on message reception, covariance values, and | ||
| * fix status. | ||
| */ | ||
| class GpsDiagnostics : public BaseDiagnostics { | ||
| public: | ||
| /** | ||
| * @brief Construct a GPSDiagnostics instance. | ||
| * @param node The ROS2 node to attach to. | ||
| * @param topic The topic of the GPS to monitor. | ||
| */ | ||
| GpsDiagnostics(rclcpp::Node::SharedPtr node, const std::string& topic); | ||
|
|
||
| private: | ||
| /// The ROS2 node | ||
| rclcpp::Node::SharedPtr node_; | ||
|
|
||
| /// Subsciber for the GPS topic | ||
| rclcpp::Subscription<sensor_msgs::msg::NavSatFix>::SharedPtr sub_gps; | ||
|
|
||
| /// Indication of whether a GPS message is received (true) or not (false) | ||
| bool gps_msg_received = false; | ||
|
|
||
| /// Header time in seconds from latest received GPS data | ||
| rclcpp::Time latest_msg_time; | ||
| /// Covariance value from latest received GPS data | ||
| double latest_covariance = 0.0; | ||
| /// Fix status from latest received GPS data | ||
| int latest_fix_status = -1; | ||
|
|
||
| /// The number of seconds of having received no data until the GPS signal is | ||
| /// deemed to be unstable | ||
| double no_data_received_limit = 5.0; | ||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Could be more semantically meaningful if this was a Also, no need for Also also, could be nice to put these into variables that are declared/gotten in the nodes. That way we keep the configuration in the launch files or even |
||
|
|
||
| /// Indication of whether a high covariance is detected (true) or not (false) | ||
| bool high_covariance_detected = false; | ||
| /// Start time of the detected high covariance value | ||
| rclcpp::Time high_covariance_start_time; | ||
|
|
||
| /// The limit of the GPS' covariance value, where a higher value indicates a | ||
| /// weak signal | ||
| double gps_covariance_limit = 30.0; | ||
| /// The number of seconds of ERROR status until the GPS signal is officially | ||
| /// deemed to be unstable | ||
| double gps_signal_instability_limit = 5.0; | ||
|
|
||
| /** | ||
| * @brief Monitor the GPS topic and save the data received. | ||
| * @param msg GPS fix message. | ||
| */ | ||
| void gps_cb(const sensor_msgs::msg::NavSatFix::SharedPtr msg); | ||
|
|
||
| /** | ||
| * @brief Evaluate the monitored data and update the diagnostic status. | ||
| * @param now current time. | ||
| */ | ||
| void evaluate(rclcpp::Time now) override; | ||
| }; | ||
|
|
||
| #endif // GPS_DIAGNOSTICS_HPP_ | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nitpick: I would vote in favor of naming our nodes
${PROJECT_NAME}_nodeif there is only one node for this package.