首页 > 技术文章 > ROS2学习之旅(6)——理解ROS2 Graph中的服务(Service)

love-robot 2021-07-13 21:55 原文

服务是ROS Graph中节点之间相互通信的一种方式。服务基于呼叫-响应模型,而不是话题的发布者-订阅者模型。话题允许节点订阅数据流并获得持续更新,而服务只有在客户端特定调用时才提供数据,一个server只能提供一种service。

1.准备

运行/turtlesim/teleop_turtle两个节点,分别在两个终端运行:

ros2 run turtlesim turtlesim_node
ros2 run turtlesim turtle_teleop_key

此时,出现窗口:

2.ros2 service list

在新终端中运行ros2 service list命令将返回系统中当前活动的所有服务的列表:

/clear
/kill
/reset
/spawn
/teleop_turtle/describe_parameters
/teleop_turtle/get_parameter_types
/teleop_turtle/get_parameters
/teleop_turtle/list_parameters
/teleop_turtle/set_parameters
/teleop_turtle/set_parameters_atomically
/turtle1/set_pen
/turtle1/teleport_absolute
/turtle1/teleport_relative
/turtlesim/describe_parameters
/turtlesim/get_parameter_types
/turtlesim/get_parameters
/turtlesim/list_parameters
/turtlesim/set_parameters
/turtlesim/set_parameters_atomically

可以看到两个节点具有相同的6个服务,其名称中包含parameters。几乎ROS 2中的每个节点都有这些基础服务,这些服务是参数构建的基础。在本节中,参数services省略,下节讨论。

可以看到与turtle1相关的服务有:

/clear
/kill
/reset
/spawn
/turtle1/set_pen
/turtle1/teleport_absolute
/turtle1/teleport_relative

3.ros2 service type

服务消息具有描述服务的请求和响应的两种数据类型。服务类型的定义类似于话题类型,服务消息类型有两个部分:一个消息类型用于请求,另一个消息类型用于响应。

运行如下命令可以得到服务的类型:

ros2 service type <service_name>

查看/clear服务的类型,在终端运行:

ros2 service type /clear

此时,终端返回:

std_srvs/srv/Empty

Empty类型意味着服务调用在发出请求时不发送数据,在接收响应时不接收数据。

3.1ros2 service list -t

想要查看所有服务的类型,可以在终端输入:

ros2 service list -t

此时,返回:

/clear [std_srvs/srv/Empty]
/kill [turtlesim/srv/Kill]
/reset [std_srvs/srv/Empty]
/spawn [turtlesim/srv/Spawn]
/teleop_turtle/describe_parameters [rcl_interfaces/srv/DescribeParameters]
/teleop_turtle/get_parameter_types [rcl_interfaces/srv/GetParameterTypes]
/teleop_turtle/get_parameters [rcl_interfaces/srv/GetParameters]
/teleop_turtle/list_parameters [rcl_interfaces/srv/ListParameters]
/teleop_turtle/set_parameters [rcl_interfaces/srv/SetParameters]
/teleop_turtle/set_parameters_atomically [rcl_interfaces/srv/SetParametersAtomically]
/turtle1/set_pen [turtlesim/srv/SetPen]
/turtle1/teleport_absolute [turtlesim/srv/TeleportAbsolute]
/turtle1/teleport_relative [turtlesim/srv/TeleportRelative]
/turtlesim/describe_parameters [rcl_interfaces/srv/DescribeParameters]
/turtlesim/get_parameter_types [rcl_interfaces/srv/GetParameterTypes]
/turtlesim/get_parameters [rcl_interfaces/srv/GetParameters]
/turtlesim/list_parameters [rcl_interfaces/srv/ListParameters]
/turtlesim/set_parameters [rcl_interfaces/srv/SetParameters]
/turtlesim/set_parameters_atomically [rcl_interfaces/srv/SetParametersAtomically]

4.ros2 service find

如果需要查找指定类型的所有服务,可以使用此命令:

ros2 service find <type_name>

例如,想要找到所有服务类型为Empty的服务,可以运行:

ros2 service find std_srvs/srv/Empty

此时,终端返回:

/clear
/reset

5.ros2 interface show

想要获得服务消息的结构,可以运行:

ros2 interface show <type_name>.srv

查看Empty的消息结构:

ros2 interface show std_srvs/srv/Empty

此时,会返回:

---

--将请求结构(上)与响应结构(下)分开,如前所述,Empty类型不发送或接收任何数据。因此,它的结构是空白的。

检查一个具有发送和接收数据类型的服务,比如/spawn。从ros2 service list -t的运行结果中,可以知道/spawn的类型是turtlesim/srv/ Spawn

要查看/spawn调用和请求中的参数,运行命令:

ros2 interface show turtlesim/srv/Spawn
float32 x
float32 y
float32 theta
string name # Optional.  A unique name will be created and returned if this is empty
---
string name

--上面的信息告诉我们调用/spawn所需的参数。x、y和theta决定了新生小海龟的位置,而name是可选的。

--下面的信息是从调用中获得的响应的数据类型。

6.ros2 service call

在已知服务类型以及该类型参数的结构时,可以使用以下方法调用服务:

ros2 service call <service_name> <service_type> <arguments>

'<arguments>'部分是可选的。例如,空类型的服务没有任何参数:

ros2 service call /clear std_srvs/srv/Empty

此命令将清除turtlesim窗口中已绘制的任何线条。

接下来通过调用/spawn并输入参数来生成一个新的海龟。'<arguments>'在一个来自命令行的服务调用中需要使用YAML语法。

在终端运行:

ros2 service call /spawn turtlesim/srv/Spawn "{x: 2, y: 2, theta: 0.2, name: ''}"

在终端得到服务响应:

waiting for service to become available...
requester: making request: turtlesim.srv.Spawn_Request(x=2.0, y=2.0, theta=0.2, name='')

response:
turtlesim.srv.Spawn_Response(name='turtle2')

7.总结

节点可以使用ROS2中的服务进行通信,是一种请求/响应模式,客户端发出请求,节点提供服务和处理服务请求并生成一个响应。

当不希望使用一个服务来连续调用,话题或者动作会更合适。

如果给您带来帮助,希望能给点个关注,以后还会陆续更新有关机器人的内容,点个关注不迷路~欢迎大家一起交流学习。

都看到这了,点个推荐再走吧~

未经允许,禁止转载。

推荐阅读