C++ Workspaces
ros2inspector has first-class support for C++ packages using Tree-sitter for accurate AST-level parsing.
What it detects
For C++ nodes, ros2inspector finds:
- Classes inheriting from
rclcpp::Node - Classes inheriting from
rclcpp_lifecycle::LifecycleNode - All
create_publisher<T>(),create_subscription<T>(),create_service<T>(),create_client<T>()calls - Template type arguments resolved to message type strings
- Action servers and clients
Typical C++ node
#include "rclcpp/rclcpp.hpp"
#include "geometry_msgs/msg/twist.hpp"
#include "nav_msgs/msg/odometry.hpp"
class MyController : public rclcpp::Node
{
public:
MyController() : Node("my_controller")
{
cmd_pub_ = this->create_publisher<geometry_msgs::msg::Twist>("/cmd_vel", 10);
odom_sub_ = this->create_subscription<nav_msgs::msg::Odometry>(
"/odom", 10,
std::bind(&MyController::odomCallback, this, std::placeholders::_1)
);
}
private:
void odomCallback(const nav_msgs::msg::Odometry::SharedPtr msg) {}
rclcpp::Publisher<geometry_msgs::msg::Twist>::SharedPtr cmd_pub_;
rclcpp::Subscription<nav_msgs::msg::Odometry>::SharedPtr odom_sub_;
};
ros2inspector extracts:
Node: MyController
language: cpp
publishers: ["/cmd_vel"]
publisher_types: ["geometry_msgs/Twist"]
subscriptions: ["/odom"]
subscription_types: ["nav_msgs/Odometry"]
Lifecycle nodes
#include "rclcpp_lifecycle/lifecycle_node.hpp"
class MySensor : public rclcpp_lifecycle::LifecycleNode
{
public:
MySensor() : LifecycleNode("my_sensor")
{
scan_pub_ = this->create_publisher<sensor_msgs::msg::LaserScan>("/scan", 10);
}
// ...
};
This is detected the same way as a regular rclcpp::Node.
Mixed Python + C++ workspaces
ros2inspector handles both in the same workspace scan:
ros2inspector nodes
┌──────────────────┬──────────────┬──────────┬───────────────────────┐
│ Node │ Package │ Language │ Publishers │
├──────────────────┼──────────────┼──────────┼───────────────────────┤
│ MyController │ my_pkg │ cpp │ /cmd_vel │
│ MySensor │ sensor_pkg │ cpp │ /scan │
│ DataProcessor │ proc_pkg │ python │ /processed_data │
└──────────────────┴──────────────┴──────────┴───────────────────────┘
Filter to C++ only:
ros2inspector packages --filter cpp
Known limitations
Template metaprogramming
Topic names computed via template metaprogramming are not resolved:
// Not detected
template<typename T>
class GenericNode : public rclcpp::Node {
auto pub_ = create_publisher<T>(TopicName<T>::value, 10);
};
Macro-generated nodes
Nodes registered via PLUGINLIB_EXPORT_CLASS or custom macros may not be detected if the class definition is hidden inside the macro.
Dynamic topic names from parameters
// Not captured — flagged as has_dynamic_names: true
auto topic = this->get_parameter("topic").as_string();
pub_ = create_publisher<std_msgs::msg::String>(topic, 10);
Header files
ros2inspector parses .cpp, .hpp, and .h files. If your node class is defined in a header file, it will be detected correctly.
Performance
C++ parsing with Tree-sitter is fast (~50ms per file), and results are cached. A 20-package C++ workspace typically analyzes in under 2 seconds after the first run.