ROS2 Fleet Coordinator V1: From Task Submission to Route Dispatch

ROS2

Posted by Bruce Lee on 2025-04-20

ROS2 Fleet Coordinator V1: From Task Submission to Route Dispatch

ros2-fleet-coordinator does not start by solving advanced fleet optimization,
conflict resolution, or full Nav2 integration. The first milestone is more
fundamental: build the smallest runnable coordination loop for a multi-robot
fleet.

At this stage, the loop is:

robot state reporting -> task submission -> idle robot selection -> waypoint route planning -> task assignment -> simulated execution -> completion feedback

From an engineering perspective, the current version is not trying to answer
“what is the globally optimal fleet schedule?” It is answering an earlier and
more important question: can task flow, state flow, and route flow be connected
into a coherent system process?

This matters because early-stage robotics projects often fall into two traps:
they either have architecture diagrams without data moving through the system,
or they have separate ROS nodes without a complete end-to-end loop. V1 is
about closing that gap.


Package Boundaries

The workspace is organized into five packages:

  • fleet_msgs
  • fleet_manager
  • robot_agent
  • path_planner
  • fleet_bringup

The important point is not simply that this split is conventional. The useful
part is that the ownership boundaries are clear.

fleet_msgs

fleet_msgs is the interface layer. It owns the shared messages and services
used across the system.

This package keeps the contract explicit. It prevents fleet_manager,
path_planner, and robot_agent from embedding each other’s local data
assumptions. It also gives future schema changes a single place to land.

Without this layer, each node would tend to invent its own topic payloads, and
coupling would grow quickly.

fleet_manager

fleet_manager is the central dispatch node. In the current version, a more
precise description is:

task intake + idle robot selection + route planning request + assignment publication

It is not yet a high-level optimizer. Its strategy is closer to a first-idle
dispatcher, which is appropriate for validating the core execution path.

robot_agent

Each robot is represented by one robot_agent node. The agent reports robot
state, receives task assignments, advances through route waypoints, and
publishes idle, executing, and completed state transitions.

In other words, it is a local execution state machine.

path_planner

path_planner deliberately uses a discrete waypoint graph and BFS. The current
focus is not continuous-space navigation. It is task-level coordination.

For an unweighted waypoint graph, BFS is the smallest correct planning method
that still produces deterministic, inspectable routes.

fleet_bringup

fleet_bringup owns launch and demo configuration. This package is easy to
undervalue, but in ROS projects bringup is part of the runnable system. Without
it, the project is just a collection of source files.


What the System Is Actually Connecting

Earlier project notes show that the main gap was not an isolated algorithmic
bug. Tasks could exist inside the manager, but the system still needed a real
planning request, a real assignment publication, and a real execution-completion
feedback path.

Having a task queue, a robot state topic, a planner package, and an agent
package does not mean the system is closed. Those parts must participate in one
observable process:

submit_task -> select robot -> request route -> publish assignment -> execute route -> report completed

Only after that path works does it make sense to discuss conflict detection,
priority scheduling, task reassignment, or deeper navigation integration.


The Minimal Process State Machine

The current system can be understood as a process state machine:

(no task, robot idle, no assignment)
-> (task enters pending queue)
-> (manager selects an idle robot)
-> (planner returns route_waypoints)
-> (manager publishes TaskAssignment)
-> (robot_agent enters executing)
-> (robot_agent advances current_waypoint)
-> (robot_agent reports completed)
-> (manager treats the robot as idle again)

This framing is useful because the key question is not only whether a function
compiles or returns a value. The key question is whether state transitions
remain valid across multiple ROS nodes.


Why fleet_manager Depends on Planning

fleet_manager keeps the scheduling semantics separate from the route
semantics. It does not compute the path by itself. It calls path_planner
through a service and only publishes a TaskAssignment after a route is
available.

This separation has two direct benefits:

  • the manager stays focused on dispatch decisions;
  • the planner can later be replaced with A*, Dijkstra, or a reservation-aware
    planner without rewriting the manager’s core role.

The cost is also clear: V1 dispatch is synchronously dependent on successful
route planning. That is acceptable while the goal is minimal correctness. If
planning latency or failure handling becomes more important, the system will
need another layer of lifecycle state.

One practical detail is especially important: the manager preserves assignment
state after a robot has just been assigned but before the agent has reported
executing. ROS topic state is not an atomic transition. There is a timing
gap between “the manager published an assignment” and “the robot reported that
it is executing.” The manager must protect that gap or it may incorrectly treat
the robot as idle again.


Why BFS Is the Right Initial Planner

It is tempting to ask why the planner is not A*, Dijkstra, or Nav2. For V1, BFS
is the right choice because the map is an unweighted waypoint graph.

The engineering value is:

  • deterministic behavior;
  • low debugging cost;
  • routes that are easy to explain;
  • enough correctness to validate the manager-agent task path.

The planner splits a transport task into two segments:

start -> pickup

and

pickup -> dropoff

Then it joins the two segments into one route. This is important because
pickup is not a hint. It is a task constraint.


Why robot_agent Closes the Loop

The current agent is not a real base controller and does not run a full
navigation stack. Its job is simpler and necessary:

  1. receive TaskAssignment;
  2. store route_waypoints;
  3. advance through the route on a timer;
  4. update current_waypoint;
  5. publish executing, completed, and idle.

From a system point of view, the agent turns a static assignment into dynamic
state feedback. Without it, the manager can only say “I believe I assigned the
task.” With it, the system can observe that the task actually moved through an
execution lifecycle.

The agent also supports waypoint position parameters and fallback demo
coordinates. That is a small but useful step toward a more realistic
RobotState: the state message carries both symbolic waypoint identity and a
position representation that other nodes can consume.


V1 as a Discrete-Event Coordination System

Although the project is built with ROS 2 and is framed as robotics software,
V1 is best understood as a topic/service-based discrete-event coordination
system.

The main state variables are not continuous control inputs. They are:

  • whether a robot is idle;
  • whether a task is pending;
  • whether route planning succeeded;
  • which waypoint the robot has reached;
  • whether the task has completed.

The real complexity is therefore in cross-node state consistency, request and
publication ordering, and assignment lifecycle management.

This is why the project documentation emphasizes a complete assignment and
completion flow. At this stage, the greatest risk is not that the algorithm is
too simple. The greater risk is that system state becomes inconsistent across
nodes.


Current Boundaries

V1 still has clear limits.

First, there is no conflict detection or reservation mechanism. A route is
currently feasible for one robot, not globally safe for the whole fleet.

Second, the dispatch strategy is first-idle. It does not yet consider distance,
battery level, priority competition, or current workload.

Third, runtime validation is partly constrained by the sandbox environment.
The project notes record DDS socket permission issues. In ROS 2, “nodes can
start” and “the full distributed loop has been verified” are not the same
thing. Environment restrictions can look like code defects unless they are
tracked separately.


Why This Is a Good Engineering Starting Point

The project is valuable because it keeps the first version small. The graph is
discrete, the planner is BFS, the agent simulates execution, and the scheduler
uses first-idle dispatch.

That compression is not a weakness. It is control over engineering complexity.
Multi-robot systems can easily introduce scheduling complexity, navigation
complexity, concurrency complexity, communication complexity, and environment
complexity all at once. If all of those enter the system together, debugging
becomes layer confusion.

V1 takes a more stable path:

  1. make the interfaces explicit;
  2. close the task loop;
  3. add conflict control;
  4. improve scheduling;
  5. consider heavier navigation integration.

That is the right order for this stage of the project.


If you like this blog or find it useful for you, you are welcome to comment on it. You are also welcome to share this blog, so that more people can participate in it. All the images used in the blog are my original works or AI works, if you want to take it,don't hesitate. Thank you !