【问题标题】:Get only MQ9 messages that belong to a group "2" in C++在 C++ 中仅获取属于组“2”的 MQ9 消息
【发布时间】:2019-09-17 15:40:05
【问题描述】:

我正在尝试将 IBM MQ 客户端 9 与 C++ 一起使用。我只想阅读组 id 为“2”的邮件。我已经尝试了一切,但它只是不起作用。有人可以帮忙吗?

我尝试设置 groupId 和 flag 以匹配组。

MQGET

gmoptions.setMatchOptions(MQMO_MATCH_GROUP_ID);
MQBYTE24 bGroupId("2");
ImqBinary _groupId;
_groupId.set(bGroupId, sizeof(bGroupId));
message.setGroupId(_groupId);
q->get(message, gmoptions);

MQPUT

MQBYTE24 bGroupId("2");
ImqBinary _groupId;
_groupId.set(bGroupId, sizeof(bGroupId));
message.setGroupId(_groupId);
ImqPutMessageOptions pmo;
pmo.setOptions(MQPMO_LOGICAL_ORDER);
pmo.setRecordFields(MQPMRF_GROUP_ID);
q->put(message, pmo);

mqget 应该能够获取 groupId "2" 的所有 msg,但它不能。虽然它可以在我删除 setMatchOptions 后立即读取消息。

基本上,我想使用组 ID 作为过滤器,其中服务器实例 1 将仅读取组 1 中的消息,服务器实例 2 将仅读取组 2 中的消息,依此类推,而不是为每个服务器实例创建单独的队列。

如果组 id 仅用于批处理而不是过滤,但不确定如何在 C++ 中“使用 MQSUB 和 MQOPEN 函数调用进行选择”,可能会帮助我 https://www.ibm.com/support/knowledgecenter/SSFKSJ_9.0.0/com.ibm.mq.dev.doc/q022990_.htm

有没有 MQSETMP 的 C++ 等价物?我在 ImqQueue 或 ImqObject 中找不到任何可以让我设置消息属性或 selectionString 的接口。

【问题讨论】:

  • 您能否使用amqsbcg 示例程序浏览groupId "2" 的消息并提供GroupId 行的输出,它可能类似于GroupId : X'000000000000000000000000000000000000000000000000'
  • 通常此字段与队列管理器一起使用是自动分段消息(例如:设置消息标志MQMF_SEGMENTATION_ALLOWED。每个唯一消息组的消息将具有唯一的组 ID 以及每个消息具有序列号(例如:1、2、3)和整个消息中的偏移量,组中的最后一条消息将带有一个标志,指示它是最后一条消息。
  • 应用程序也可以使用它来创建消息组。但正如您指出的那样,它是一个 24 字节字段,您只是将其设置为 ascii 字符“2”的字节值。
  • C++ 不支持发布订阅。看到这个答案stackoverflow.com/questions/57101776/…
  • 要回答您的最新更新,请参阅我提供的链接。 C++ 类已稳定在 v6 级别,并且从 7.0 或更高版本起没有进行任何增强。消息属性是在 7.0 中添加的。您需要使用 C API 来使用这些功能。你有什么理由不回复我要离开你的cmets?

标签: c++ ibm-mq


【解决方案1】:

我不认为你这样做是正确的。

IBM 发布了一个 Java/MQ 示例程序来获取名为 GetGroup.java 的组中的消息。你可以找到它here。您可以将其用作 C++ 程序的模型。

基本上,代码从队列中检索消息,然后检查 messageFlags 字段是否该消息是组的一部分。

if ((myMessage.messageFlags & CMQC.MQMF_MSG_IN_GROUP) == CMQC.MQMF_MSG_IN_GROUP)

如果消息是组的一部分,则代码设置 matchOptions 以匹配组并检索组中的所有消息。

注意:您可能希望为 GMO 选项添加逻辑顺序。

gmo.options |= CMQC.MQGMO_LOGICAL_ORDER;

最后,这是什么?

pmo.setRecordFields(MQPMRF_GROUP_ID);

这没有任何意义。您应该将 messageFlags 字段设置为 MQMF_MSG_IN_GROUP

【讨论】:

  • 它违背了整个目的。如果 msg 不是该组的一部分,我根本不想阅读该消息。如果我必须读取味精然后只比较组 ID,那么匹配选项 MQMO_MATCH_GROUP_ID 有什么用?队列将不断在多个组中重复获取消息,当且仅当它属于我感兴趣的单个组“2”时,我才想触摸消息。
  • 我认为您没有正确使用 MQ 消息分组。您应该阅读 MQ 知识中心。每个消息组应该有一个唯一的 id,每个消息组应该是一个有限的数字(即 5、10、20 等)。听起来您有一个接收许多不同类型消息的队列,并且您正在尝试使用 Group Id 作为某种过滤器。不是一个好主意。每个消息类型/目的都应该有自己的队列。因此,您不需要过滤消息。
  • 在 IBM MQ 中,消息可以出现在组内以允许对消息进行排序。通常,实际情况是,如果系统 A 正在为系统 B 生成消息以分批(组)消费,但系统 B 应该仅在批次中的所有消息都到达队列时才单独消费每批消息。此外,如果必须按顺序处理消息,则使用分组概念。请解释您的总体情况。
  • 是的,罗杰是对的。我正在尝试使用组 ID 作为过滤器,其中服务器实例 1 将仅读取组 1 中的消息,服务器实例 2 将仅读取组 2 中的消息,依此类推。
【解决方案2】:

您可以在 IBM MQ 中使用 SELECTORS 的概念。消息选择器是一个可变长度的字符串,应用程序使用它来仅注册其对那些具有满足选择字符串所代表的结构化查询语言 (SQL) 查询的属性的消息的兴趣。

消息选择器是一个在 JMS 规范中已经存在很长时间的概念。它 是一种将传递给应用程序的消息限制为满足 某些标准。这些标准基于消息属性的值,并且仅 消息属性的值。重要的是要了解选择不能 基于消息负载的任何值,仅基于消息属性值。

在您的情况下,PUT 应用程序必须通过在 MQMD 或 MQRFH2 标头中填充特定主题字符串并使用 MQ 接口函数调用来放置消息,您应该只能选择具有特定值的消息,这些值在您的case 是 GroupId 值。

以下是该概念的几个参考链接: https://www.ibm.com/support/knowledgecenter/SSFKSJ_7.5.0/com.ibm.mq.dev.doc/q022990_.htm

http://publib.boulder.ibm.com/infocenter/ieduasst/v1r1m0/topic/com.ibm.iea.wmq_v7/wmq/7.0/MQI/iea_330_wmqv7_API_3_Selectors.pdf ==> 下载 PDF

了解消息属性 => https://www.ibm.com/support/knowledgecenter/en/SSFKSJ_8.0.0/com.ibm.mq.dev.doc/q022920_.htm

【讨论】:

  • c++ API 是否支持这个,我没想到。
  • 我浏览了类似于 JMS 的 XMS for C++ 的以下链接。 ibm.com/support/pages/ia94-ibm-message-service-client-xms-cc。使用它应该可以根据可以下载的链接中存在的 ia94.pdf 进行消息选择。
  • @frabar - 是否有任何用于选择器的 C/C++ 示例?
  • 是否有任何 C++ 等效的 MQSETMP ?我无法在 ImqQueue 或 ImqObject 中找到任何可以让我设置消息属性或 selectionString 的接口。
  • 另一个铁是使用XMS C++ API。或者重新考虑一下为什么不想使用 2 个队列。
猜你喜欢
  • 2016-05-09
  • 1970-01-01
  • 2023-03-16
  • 1970-01-01
  • 2019-04-14
  • 1970-01-01
  • 2021-06-11
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多