ROS Service command line tools – practical example (rosservice and rossrv)

This tutorial is a practical guide on how to use rosservice and rossrv command line tools to debug a ROS service.

You know those command line tools are useful, but it’s hard for you to really understand how to use them efficiently?

Well, this tutorial is for you. I’ll show you step by step exactly how to do through a real example.

Code example

Let’s create a simple ROS service server. For this example I’m using Python to create a “/add_two_ints” service which receives 2 numbers and return the sum.

import rospy
from rospy_tutorials.srv import AddTwoInts

def handle_add_two_ints(req):
    result = req.a + req.b
    rospy.loginfo("Sum of " + str(req.a) + " and " + str(req.b) + " is " + str(result))
    return result

if __name__ == '__main__':
    rospy.init_node("add_two_ints_server")
    rospy.loginfo("Add two ints server node created")

    service = rospy.Service("/add_two_ints", AddTwoInts, handle_add_two_ints)
    rospy.loginfo("Service server has been started")

    rospy.spin()

Let’s run this code:

  • Don’t forget to start roscore in another terminal, to create a ROS master.
  • Make the file executable: chmod +x add_two_ints.py.
  • Start the node: python add_two_ints.py (you can also use rosrun if you want).

Alright, the node is now running and it is advertising a Service server. Let’s now find out everything about this service server we’ve just created, using the ROS command line tools!

Find the advertised service (rosservice list)

Use rosservice list to find all the currently active services that where launched after you started the ROS master.

$ rosservice list 
/add_two_ints
/add_two_ints_server/get_loggers
/add_two_ints_server/set_logger_level
/rosout/get_loggers
/rosout/set_logger_level

First good news, we found the “/add_two_ints” service. As you can see, 5 services are currently active.

If you have a long list and want to find a particular service, use grep:

$ rosservice list | grep add_two_ints
/add_two_ints
/add_two_ints_server/get_loggers
/add_two_ints_server/set_logger_level

Get more details about this service (rosservice info)

Now that we have found the service, let’s see if we can get more details about it.

Use rosservice info:

$ rosservice info /add_two_ints
Node: /add_two_ints_server
URI: rosrpc://ros-pc:38201
Type: rospy_tutorials/AddTwoInts
Args: a b

A few useful info here:

  • Node: this is the node advertising the service, so you know where it comes from.
  • Type: maybe the most important info here. This is the service definition (.srv file) you need to use in order to call the service.
  • Args: a quick resume about the request part of the service definition. This gives you the name of the arguments you need to send (without the detailed types).

Find out what data you need to send and receive (rossrv show)

Once you have found the definition (type) of the service you want to use, you’d like to know what exactly is in this definition.

Use rossrv show:

$ rossrv show rospy_tutorials/AddTwoInts
int64 a
int64 b
---
int64 sum

Now, you know that:

  • The request consists of two int64 numbers, ‘a’ and ‘b’ (with only the “Args” field we got from rosservice info, we couldn’t know for sure the type).
  • The service will return a response, which consists of one int64 number called ‘sum’.

Call the service (rosservice call)

You now have all the required info to call the service. You know the name of the service, the service definition you need to use, and precisely what’s inside this definition.

Use rosservice call:

$ rosservice call /add_two_ints "a: 4
b: 3" 
sum: 7

(hint: after you’ve written the name of the service, press “TAB” 2 times to get the structure of the request message auto-completed. Then with your keyboard arrows you can change the values)

And… It works!

Note that calling services with many arguments in the request message won’t be practical. Anyway, using the command line tool is only useful for testing and debugging. The obvious next step is to create a service client in another node (rospy or roscpp), using all the info that you got from the previous steps.

Closing the loop

So, from the name of the service we were able to find many info, including the name of the node which advertises it.

Let’s execute rosnode info on this node we found:

$ rosnode info /add_two_ints_server 
--------------------------------------------------------------------------------
Node [/add_two_ints_server]
Publications: 
 * /rosout [rosgraph_msgs/Log]

Subscriptions: None

Services: 
 * /add_two_ints
 * /add_two_ints_server/get_loggers
 * /add_two_ints_server/set_logger_level


contacting node http://ros-pc:33215/ ...
Pid: 4944
Connections:
 * topic: /rosout
    * to: /rosout
    * direction: outbound
    * transport: TCPROS

As you can see, from a node info we can also retrieve all services started from this node.

The loop is now complete. From any info you have (node, service name) you can find all the other info using ROS command line tools.

ROS Service command line tools: more about rosservice and rossrv

You have now all the required practical knowledge to debug your ROS services with a terminal.

Note that I didn’t list all the rosservice and rossrv functions, only the most useful ones.

So that you know, you can list all service definitions (.srv files) available on your ROS environment with rossrv list. Using grep with this command line tool can be useful to see if you’re missing a service definition (not installed or not compiled) so that you can fix it.

For the reference of all available functions, just type rosservice and rossrv with no argument.

Leave a Comment