警告

您正在阅读的 ROS 2 文档版本已达到 EOL(生命周期结束),不再受官方支持。如果您想了解最新信息,请访问 Jazzy.

编写简单的服务和客户端(Python)

目标 使用 Python 创建并运行服务和客户端节点。

辅导水平: 初学者

时间 20 分钟

背景介绍

何时 结点 使用 服务其中,发送数据请求的节点称为客户节点,响应请求的节点称为服务节点。请求和响应的结构由一个 .srv 锉刀

这里使用的示例是一个简单的整数加法系统:一个节点请求计算两个整数之和,另一个节点响应结果。

先决条件

在前面的教程中,您学习了如何 创建工作区创建软件包.

任务

1 创建软件包

打开一个新终端,然后 为您的 ROS 2 安装提供源代码 以便 玫瑰2 命令即可运行。

导航进入 dev_ws 目录中创建的 上一个教程.

回顾一下,软件包应在 来源 目录,而不是工作区的根目录。导航到 dev_ws/src 并创建一个新软件包:

ros2 pkg create --build-type ament_python py_srvcli --dependencies rclpy example_interfaces

您的终端将返回一条信息,验证是否创建了软件包 py_srvcli 及其所有必要的文件和文件夹。

"(《世界人权宣言》) --依赖 参数会自动在 package.xml. 接口示例 是一个软件包,其中包括 .srv文件 您需要对请求和回复进行结构化设计:

int64 a
int64 b
---
int64 sum

前两行是请求的参数,破折号下面是响应。

1.1 更新 package.xml

因为您使用了 --依赖 选项,就不必在创建软件包时手动将依赖关系添加到 package.xml.

不过,请务必一如既往地将说明、维护者的电子邮件和姓名以及许可证信息添加到 package.xml.

<描述>;Python 客户 服务器 教程</description>;
维护者 电子邮件="[email protected]";>;您的 名称维护人员</maintainer>;
许可证阿帕奇 许可证 2.0</license>;

1.2 更新 setup.py

setup.py 文件的 维护者, 维护者电子邮件, 描述许可 领域:

维护者='您的姓名';,
维护者电子邮件='[email protected]';,
描述='Python 客户端服务器教程';,
许可='阿帕奇许可证 2.0';,

2 写入服务节点

内部 dev_ws/src/py_srvcli/py_srvcli 目录下,新建一个名为 service_member_function.py 并粘贴以下代码:

 example_interfaces.srv 舶来品 添加两个字符

舶来品 rclpy
 rclpy.node 舶来品 节点


 最小服务(节点):

    捍卫 启动(自我):
        棒极了().启动('minimal_service';)
        自我.服务 = 自我.创建服务(添加两个字符, 'add_two_ints', 自我.add_twoo_ints_callback)

    捍卫 add_twoo_ints_callback(自我, 要求, 回应):
        回应.数额 = 要求.a + 要求.b
        自我.get_logger().信息('收到请求\na: %d b: %d' % (要求.a, 要求.b))

        返回 回应


捍卫 主要(参数=):
    rclpy.启动(参数=参数)

    最小服务 = 最小服务()

    rclpy.后旋(最小服务)

    rclpy.关闭()


如果 姓名____ == '__main__';:
    主要()

2.1 检查代码

第一个 舶来品 语句导入 添加两个字符 服务类型 接口示例 一揽子计划以下内容 舶来品 语句导入了 ROS 2 Python 客户端库,特别是 节点 类。

 example_interfaces.srv 舶来品 添加两个字符

舶来品 rclpy
 rclpy.node 舶来品 节点

"(《世界人权宣言》) 最小服务 类的构造函数将节点初始化为名称为 最小服务.然后,创建服务并定义类型、名称和回调。

捍卫 启动(自我):
    棒极了().启动('minimal_service';)
    自我.服务 = 自我.创建服务(添加两个字符, 'add_two_ints', 自我.add_twoo_ints_callback)

服务回调的定义是接收请求数据、求和并将和作为响应返回。

捍卫 add_twoo_ints_callback(自我, 要求, 回应):
    回应.数额 = 要求.a + 要求.b
    自我.get_logger().信息('收到请求\na: %d b: %d' % (要求.a, 要求.b))

    返回 回应

最后,主类会初始化 ROS 2 Python 客户端库,实例化 最小服务 类来创建服务节点,并旋转节点以处理回调。

2.2 添加入口

玫瑰2 运行 命令来运行您的节点,您必须将入口点添加到 setup.py 位于 dev_ws/src/py_srvcli 目录)。

控制台脚本 括号:

'service = py_srvcli.service_member_function:main';,

3 写入客户节点

内部 dev_ws/src/py_srvcli/py_srvcli 目录下,新建一个名为 client_member_function.py 并粘贴以下代码:

舶来品 系统

 example_interfaces.srv 舶来品 添加两个字符
舶来品 rclpy
 rclpy.node 舶来品 节点


 最小客户端同步(节点):

    捍卫 启动(自我):
        棒极了().启动('minimal_client_async';)
        自我. = 自我.创建客户端(添加两个字符, 'add_two_ints')
        虽然  自我..等待服务(超时秒数=1.0):
            自我.get_logger().信息('服务不可用,请再次等待...';)
        自我.要求 = 添加两个字符.要求()

    捍卫 发送请求(自我):
        自我.要求.a = int(系统.参数[1])
        自我.要求.b = int(系统.参数[2])
        自我.未来 = 自我..调用同步(自我.要求)


捍卫 主要(参数=):
    rclpy.启动(参数=参数)

    最小客户端 = 最小客户端同步()
    最小客户端.发送请求()

    虽然 rclpy.好的():
        rclpy.自旋一次(最小客户端)
        如果 最小客户端.未来.完成的():
            尝试:
                回应 = 最小客户端.未来.结果()
            除开 例外情况 作为 e:
                最小客户端.get_logger().信息(
                    '服务调用失败 %r' % (e,))
            不然:
                最小客户端.get_logger().信息(
                    'add_two_ints 的结果: for %d + %d = %d' %
                    (最小客户端.要求.a, 最小客户端.要求.b, 回应.数额))
            断裂

    最小客户端.destroy_node()
    rclpy.关闭()


如果 姓名____ == '__main__';:
    主要()

3.1 检查代码

唯一不同的是 舶来品 客户的语句是 舶来品 系统.客户端节点代码使用 sys.argv 来获取请求的命令行输入参数。

构造函数定义创建的客户端与服务节点的类型和名称相同。类型和名称必须匹配,客户端和服务节点才能通信。

"(《世界人权宣言》) 虽然 构造函数中的循环每秒检查一次与客户端类型和名称匹配的服务是否可用。

构造函数下面是请求定义,后面是 主要.

客户的唯一重大区别是 主要虽然 循环。循环检查 未来 来查看服务是否有响应,只要系统还在运行。如果服务发送了响应,结果将写入日志信息。

3.2 添加入口

与服务节点一样,您也必须添加一个入口点才能运行客户端节点。

"(《世界人权宣言》) 入口 您的 setup.py 文件应该是这样的

入口={
    'console_scripts';: [
        'service = py_srvcli.service_member_function:main';,
        'client = py_srvcli.client_member_function:main';,
    ],
},

4 构建和运行

运行 rosdep 在工作区的根目录 (dev_ws) 在构建前检查是否缺少依赖项:

rosdep install -i --from-path src --rosdistro dashing -y

返回工作区的根目录、 dev_ws然后创建新软件包:

colcon build --packages-select py_srvcli

打开一个新终端,导航至 dev_ws并获取设置文件:

install/setup.bash

现在运行服务节点:

ros2 运行 py_srvcli 服务

节点将等待客户端的请求。

打开另一个终端,从里面获取设置文件的源代码 dev_ws 再次。以客户节点为起点,然后是以空格分隔的任意两个整数:

ros2 run py_srvcli client 2 3

如果您选择 23例如,客户端会收到这样的回复:

[INFO] [minimal_client_async]:add_twoo_ints 的结果: for 2 + 3 = 5

返回运行服务节点的终端。您会看到它在收到请求时发布了日志信息:

[INFO] [minimal_service]:收到请求
a: 2 b: 3

进入 Ctrl+C 在服务器终端停止节点旋转。

摘要

您创建了两个节点,用于通过服务请求和响应数据。您将它们的依赖项和可执行文件添加到软件包配置文件中,这样就可以构建和运行它们,从而看到服务/客户端系统正在运行。

下一步工作

在过去的几个教程中,您一直在利用接口在主题和服务之间传递数据。接下来,您将学习如何 创建自定义界面.