当前位置: 首页 > news >正文

【FastDDS】Layer DDS之Domain ( 03-DomainParticipantListener)

Fast DDS 域参与者监听器(DomainParticipantListener)详解

一、域参与者监听器(DomainParticipantListener)基础定义

DomainParticipantListener(域参与者监听器)是一个抽象类,用于定义在域参与者(DomainParticipant)状态发生变化时触发的回调函数。默认情况下,所有回调函数均为空实现,不执行任何操作。用户需实现该类的特化版本,重写应用程序所需的回调函数;未重写的回调函数将保持空实现。

DomainParticipantListener 继承自 TopicListener(主题监听器)、PublisherListener(发布者监听器)和 SubscriberListener(订阅者监听器)。因此,它能够响应所有附加实体(Entities)上报的各类事件。由于事件始终会通知给能够处理该事件的“最具体实体监听器”,所以 DomainParticipantListener 从其他监听器继承的回调函数,仅在以下情况下才会被调用:没有其他实体能处理该事件(要么该实体未附加监听器,要么实体的 StatusMask(状态掩码)禁用了该回调函数)。

二、域参与者监听器的非标准回调函数

除了从父类继承的回调函数外,DomainParticipantListener 还额外添加了以下非标准回调函数,用于处理域内实体发现、身份认证等特定事件:

(一)on_participant_discovery():域参与者发现回调

当同一域内发现新的域参与者、已知域参与者被移除,或某域参与者的 QoS(服务质量)发生变更时,该回调函数会被触发。
该函数提供一个重载版本,包含额外的布尔型输出参数——通过此参数,发现回调可告知中间件是否需要通过 ignore_participant() 函数忽略新发现的域参与者。若需在发现回调内部忽略域参与者,应使用该重载版本,因为在监听器中直接调用 ignore_participant() 可能导致死锁。
若同时实现了两个版本的回调函数(带布尔参数和不带布尔参数),则带有 should_be_ignored(是否应忽略)布尔标志的版本优先级更高。只有当第一个回调函数中未忽略该域参与者(should_be_ignored 参数返回 false)时,才会执行第二个回调函数。

(二)on_data_reader_discovery():数据读取器发现回调

当同一域内发现新的 DataReader(数据读取器)、已知 DataReader 被移除,或某 DataReader 的 QoS 发生变更时,该回调函数会被触发。

(三)on_data_writer_discovery():数据写入器发现回调

当同一域内发现新的 DataWriter(数据写入器)、已知 DataWriter 被移除,或某 DataWriter 的 QoS 发生变更时,该回调函数会被触发。

(四)onParticipantAuthentication():域参与者身份认证回调

该回调函数用于告知远程域参与者身份认证过程的结果,包括认证成功和认证失败两种情况。需注意,此回调函数仅在启用安全功能(HAVE_SECURITY 宏定义生效)时可用。

三、自定义域参与者监听器(CustomDomainParticipantListener)示例

以下是自定义 DomainParticipantListener 的完整代码示例,实现了上述所有非标准回调函数,展示了如何处理域参与者、数据读取器、数据写入器的发现事件及身份认证事件:

class CustomDomainParticipantListener : public DomainParticipantListener
{public:CustomDomainParticipantListener(): DomainParticipantListener(){}virtual ~CustomDomainParticipantListener(){}// 域参与者发现回调(带should_be_ignored参数的重载版本)void on_participant_discovery(DomainParticipant* participant,eprosima::fastdds::rtps::ParticipantDiscoveryStatus status,const ParticipantBuiltinTopicData& info,bool& should_be_ignored) override{should_be_ignored = false; // 默认不忽略新发现的域参与者// 处理“发现新域参与者”事件if (status == eprosima::fastdds::rtps::ParticipantDiscoveryStatus::DISCOVERED_PARTICIPANT){std::cout << "New participant discovered" << std::endl; // 输出“发现新域参与者”日志// 可根据发现信息中的字段修改以下条件,判断是否忽略该域参与者bool ignoring_condition = false;if (ignoring_condition){should_be_ignored = true; // 请求忽略该新发现的域参与者}}// 处理“域参与者被移除”或“域参与者掉线”事件else if (status == eprosima::fastdds::rtps::ParticipantDiscoveryStatus::REMOVED_PARTICIPANT ||status == eprosima::fastdds::rtps::ParticipantDiscoveryStatus::DROPPED_PARTICIPANT){std::cout << "Participant lost" << std::endl; // 输出“域参与者丢失”日志}}#if HAVE_SECURITY // 仅在启用安全功能时编译此部分代码// 域参与者身份认证回调void onParticipantAuthentication(DomainParticipant* participant,eprosima::fastdds::rtps::ParticipantAuthenticationInfo&& info) override{// 处理“域参与者认证通过”事件if (info.status == eprosima::fastdds::rtps::ParticipantAuthenticationInfo::AUTHORIZED_PARTICIPANT){std::cout << "A participant was authorized" << std::endl; // 输出“域参与者认证通过”日志}// 处理“域参与者认证失败”事件else if (info.status == eprosima::fastdds::rtps::ParticipantAuthenticationInfo::UNAUTHORIZED_PARTICIPANT){std::cout << "A participant failed authorization" << std::endl; // 输出“域参与者认证失败”日志}}#endif // 结束HAVE_SECURITY条件编译块// 数据读取器发现回调void on_data_reader_discovery(DomainParticipant* participant,eprosima::fastdds::rtps::ReaderDiscoveryStatus reason,const eprosima::fastdds::rtps::SubscriptionBuiltinTopicData& info,bool& should_be_ignored) override{should_be_ignored = false; // 默认不忽略新发现的数据读取器// 处理“发现新数据读取器”事件if (reason == eprosima::fastdds::rtps::ReaderDiscoveryStatus::DISCOVERED_READER){std::cout << "New datareader discovered" << std::endl; // 输出“发现新数据读取器”日志// 可根据发现信息中的字段修改以下条件,判断是否忽略该数据读取器bool ignoring_condition = false;if (ignoring_condition){should_be_ignored = true; // 请求忽略该新发现的数据读取器}}// 处理“数据读取器被移除”事件else if (reason == eprosima::fastdds::rtps::ReaderDiscoveryStatus::REMOVED_READER){std::cout << "Datareader lost" << std::endl; // 输出“数据读取器丢失”日志}}// 数据写入器发现回调void on_data_writer_discovery(DomainParticipant* participant,eprosima::fastdds::rtps::WriterDiscoveryStatus reason,const eprosima::fastdds::dds::PublicationBuiltinTopicData& info,bool& should_be_ignored) override{// 强制转换以避免“未使用参数”的编译警告static_cast<void>(participant);static_cast<void>(info);should_be_ignored = false; // 默认不忽略新发现的数据写入器// 处理“发现新数据写入器”事件if (reason == eprosima::fastdds::rtps::WriterDiscoveryStatus::DISCOVERED_WRITER){std::cout << "New datawriter discovered" << std::endl; // 输出“发现新数据写入器”日志// 可根据发现信息中的字段修改以下条件,判断是否忽略该数据写入器bool ignoring_condition = false;if (ignoring_condition){should_be_ignored = true; // 请求忽略该新发现的数据写入器}}// 处理“数据写入器被移除”事件else if (reason == eprosima::fastdds::rtps::WriterDiscoveryStatus::REMOVED_WRITER){std::cout << "Datawriter lost" << std::endl; // 输出“数据写入器丢失”日志}}};

代码说明

  1. 构造与析构函数:自定义监听器类 CustomDomainParticipantListener 继承自 DomainParticipantListener,构造函数调用父类构造函数,析构函数为虚函数(确保子类对象销毁时正确调用父类析构逻辑)。
  2. 事件处理逻辑:每个回调函数均通过判断事件状态(如 DISCOVERED_PARTICIPANTREMOVED_READER)区分事件类型,并输出对应日志;同时提供 ignoring_condition 变量,支持根据业务需求自定义“是否忽略实体”的判断逻辑。
  3. 安全功能适配onParticipantAuthentication() 回调被包裹在 #if HAVE_SECURITY 条件编译块中,仅在启用安全功能时生效,符合 Fast DDS 的安全机制设计。
http://www.dtcms.com/a/365465.html

相关文章:

  • GEO服务商推荐:移山科技以划时代高精尖技术引领AI搜索优化新纪元
  • 淘宝京东拼多多爬虫实战:反爬对抗、避坑技巧与数据安全要点
  • 非力扣100原题
  • 力扣hot100:螺旋矩阵(边界压缩,方向模拟)(54)
  • 2 XSS
  • PLSQL导入excel数据的三种方法
  • GitHub 宕机自救指南技术文章大纲
  • 模板进阶
  • Python/JS/Go/Java同步学习(第二篇)四语言数据基本类型对照表: 老板让我统一系统数据类型?(附源码/截图/参数表/老板沉默术)
  • GitLab Milestones 深度解析:选型、竞品、成本与资源消耗
  • 本地Merge-github有新的远程提交与本地新修改
  • 创建消息队列,完成信息传输
  • 输电线路杆塔倾斜在线监测装置:技术解析与实际应用
  • 浏览器面试题及详细答案 88道(67-77)
  • 项目中 Spring Boot 配置文件未生效该如何解决
  • 网络世界漫游指南:MAC地址、MAC层与LLC层的奇幻之旅
  • 从儒略日到航天轨道:时间与坐标系的探索之旅
  • torch学习 自用
  • Ubuntu22.04下编译googletest源代码生成.so动态库
  • 现在你问「怎么剪枝」,其实就是在 循环里面提前判断,如果后面剩下的数字不够了,就不用再递归下去了。
  • 神经网络模型介绍
  • STM32的时钟系统与时钟树的配置
  • pip的缓存
  • 嵌入式人别再瞎折腾了!这8个开源项目,解决按键/队列/物联网所有痛点,小白也能抄作业
  • 【Rhino】【Python】将开放曲面转换为边界线和填充
  • Kotlin编程学习记录2
  • H3C UIS Cell 3020 G3服务器更换raid卡安装ONEStor记录
  • Python - Union联合类型注解
  • 数据库函数详解:COALESCE 到底有什么用?
  • 微硕WINSOK超低阻抗MOS管 WSD30100DN56在汽车高性能系统中的应用