Robotics From Zero
Module: Making Parts Talk

Point-to-Point vs Broadcast

When to use pub/sub and when to use request-response — understanding the trade-offs between broadcast and directed communication.

8 min read

Point-to-Point vs Broadcast

Pub/sub is a broadcast pattern — one publisher, many listeners. But not all communication fits this model. Sometimes you need to ask a specific node a question and wait for an answer.

Two Patterns, Two Use Cases

Publish-SubscribeRequest-Response (Service)
DirectionOne-to-manyOne-to-one
TimingContinuous streamOn-demand
Blocking?No — publisher doesn't waitYes — caller waits for reply
Best forSensor data, commands, state updatesConfiguration, computation, one-off queries
Point-to-point communication — request-response between two specific nodes
Point-to-point (request-response): the caller sends a request and blocks until it gets an answer. Perfect for one-off computations like path planning.
Broadcast communication — one publisher sends to all nodes, some care and some don't
Broadcast (pub/sub): the camera publishes once and the system delivers to all subscribers. Nodes that don't care simply don't subscribe.

When to Use Pub/Sub

Use pub/sub when:

  • Data flows continuously (sensor readings, motor commands)
  • Multiple consumers need the same data
  • The producer doesn't care who is consuming
  • You want fire-and-forget semantics

Examples: camera images, LiDAR scans, velocity commands, robot pose, map updates.

When to Use Request-Response

Use request-response (also called services) when:

  • You need a one-time computation (plan a path from A to B)
  • You need to query state (what are the current joint positions?)
  • You need to change configuration (set the maximum speed to 2.0 m/s)
  • The caller needs to wait for the result before proceeding

Examples: path planning request, parameter changes, calibration triggers, map saves.

Service example
# Path planning service (server side)
def handle_plan_request(request):
    start = request.start_pose
    goal = request.goal_pose
    path = a_star(start, goal, map)
    return PlanResponse(path=path, success=True)
 
service = create_service(
    name="/planning/plan_path",
    type=PlanService,
    handler=handle_plan_request
)
 
# Navigation node (client side)
client = create_client("/planning/plan_path", PlanService)
response = client.call(PlanRequest(
    start_pose=current_pose,
    goal_pose=target
))
# Blocks until the path planner responds
path = response.path

The Hybrid Approach

Real robots use both patterns together:

Continuous data (pub/sub):
  Camera → /camera/rgb → Detector → /objects
  LiDAR → /lidar/scan → Mapper → /map
  Controller → /cmd_vel → Motors
 
One-off requests (services):
  Navigation ← "plan path A→B" → Path Planner
  CLI ← "save map to disk" → Map Saver
  Config ← "set max speed" → Controller

The rule of thumb: if data flows continuously, use pub/sub. If you're asking a question, use a service.

Note

Some robot frameworks also have actions — long-running tasks with progress feedback. "Navigate to coordinates (5, 3)" is an action: it takes time, you want progress updates, and you might want to cancel it mid-way. Actions combine the request-response pattern with streaming feedback.

Scalability comparison — O(n²) point-to-point vs O(n) pub/sub connection growth
The scalability argument in one chart. Point-to-point connections grow quadratically — at 10 nodes you need 45 connections. Pub/sub stays linear at ~20.

Common Pitfalls

Using services for streaming data

Don't request camera images one at a time through a service. Each call has overhead, and you lose the decoupling benefits. Use pub/sub instead.

Using pub/sub for configuration

Publishing a "set speed" message to a topic seems convenient but has problems:

  • How do you know it was received?
  • What if multiple nodes try to set different speeds?
  • How do you query the current value?

A service call gives you a response confirming the change succeeded.

Mixing blocking and real-time

If your 100Hz control loop calls a service that takes 50ms to respond, your loop drops to 20Hz. Never put blocking service calls in time-critical loops. Either use them in a separate thread or cache the result.

What's Next?

We've seen how nodes can exchange data through pub/sub and services. But what exactly is inside those messages? In the next lesson, we'll look at message types — how data is structured, serialized, and validated.

Got questions? Join the community

Discuss this lesson, get help, and connect with other learners on r/softwarerobotics.

Join r/softwarerobotics

Related Lessons

Discussion

Sign in to join the discussion.