应用程序设计和性能注意事项
低劣的程序设计可以通过许多方式影响性能。 难以检测这些方式,因为程序可能本身执行良好,但会影响其他任务的性能。 本主题中说明了特定于进行 IBM® MQ 调用的程序的若干问题。
- 设计应用程序,以便处理与用户的思考时间并行进行:
- 显示面板并允许用户在应用程序仍在初始化的同时开始输入。
- 从不同服务器并行获取所需的数据。
- 如果将要复用连接和队列而不是重复打开和关闭、连接以及断开连接,请将其保持打开。
- 但是,仅放置一条消息的服务器应用程序应使用 MQPUT1。
- 针对大小介于 4 KB 和 100 KB 之间的消息优化队列管理器。 超大消息效率低下;发送 100 条 1 MB 的消息比发送单条 100 MB 的消息可能更好。 超小消息也效率低下。 队列管理器对于单字节消息和对于 4 KB 消息执行相同的工作量。
- 将消息保留在同一个工作单元内,以便可同时对其进行落实或退回。
- 对无需可恢复的消息使用非持久性选项。
- 如果需要将消息发送到许多目标队列,请考虑使用分发列表。
消息长度的影响
消息中的数据量可以影响处理该消息的应用程序的性能。 要使应用程序达到最佳性能,只发送消息中必不可少的数据。 例如,在记入银行帐户借方的请求中,可能需要从客户机传递到服务器应用程序的唯一信息是帐号和借记金额。
消息持久性的影响
通常会记录持久消息。 记录消息会降低应用程序的性能,因此应只对必不可少的数据使用持久消息。 如果消息中的数据可以在队列管理器停止或失败时废弃,请使用非持久消息。
如果没有足够的恢复日志空间来记录操作,那么将阻止针对持久消息执行的 MQPUT 和 MQGET 操作。 在队列管理器作业日志中,通过消息 CSQJ110E 和 CSQJ111A来指示这种情况。 确保已运行监视进程以便可管理和消除此类条件。
搜索特定消息
MQGET 调用通常检索来自队列的第一条消息。 如果使用消息描述符中的消息和相关标识(MsgId 和 CorrelId)来指定特定消息,那么队列管理器必须搜索队列,直至找到该消息为止。 以此方式使用 MQGET 调用会影响应用程序的性能。
包含不同长度的消息的队列
如果应用程序无法使用固定长度的消息,请动态增大和缩小缓冲区以适合典型消息大小。 如果应用程序发出 MQGET 调用,该调用由于缓冲区大小而失败,那么将返回消息数据的大小。 向应用程序添加代码,以便相应地调整缓冲区大小并重新发出 MQGET 调用。
同步点的频率
在同步点内发出大量 MQPUT 或 MQGET 调用而没有将其落实的程序可能会导致性能问题。 受影响队列可能会充满当前不可访问的消息,而其他任务可能在等待获取这些消息。 这在存储以及在与尝试获取消息的任务捆绑的线程方面具有影响。
MQPUT1 调用的使用
仅在您要将单条消息放在队列上的情况下,使用 MQPUT1 调用。 如果要放置多条消息,请使用 MQOPEN 调用,后跟一系列 MQPUT 调用和单个 MQCLOSE 调用。
使用中的线程数
对于 IBM MQ for Windows,应用程序可能需要大量线程。 每个队列管理器进程分配有最大可允许的应用程序线程数。
应用程序可能使用过多线程。 请考虑应用程序是否将此可能性考虑在内,并采取操作停止或报告此类情况的发生。
将持久消息放在同步点下
应在同步点下放置和获取持久消息。 这是因为在同步点外获取持久消息时,如果获取失败,那么应用程序无法知道是否已从队列取出消息,以及是否在获取消息后,该消息也已丢失。 在同步点下获取持久消息时,如果任何操作失败,那么会回滚事务且持久消息不会丢失,因为它仍在队列上。
同样,在放置持久消息时,请将其放在同步点下。 在同步点下放置和获取持久消息的另一个原因是 IBM MQ 中的持久消息代码针对同步点进行了大量优化。 因此,在同步点下放置和获取持久消息比在同步点外放置和获取持久消息更快速。
如果应用程序确实将持久消息放在同步点之外,队列管理器将检查是否可以代表应用程序创建隐式同步点。 如果队列管理器可以执行此操作,那么可以包括放置在同步点中,并将其自动提交。 请参阅 多平台上的隐式同步点 以获取更详细的描述。
但是,在同步点外部放置和获取非持久消息的速度更快,因为 IBM MQ 中的非持久代码已针对同步点外部进行了优化。 放置和获取持久消息以磁盘速度进行,因为持久消息持久存储到磁盘。 但是,放置和获取非持久消息以 CPU 速度进行,因为没有涉及任何磁盘写操作,即使在使用同步点时也如此。
如果应用程序正在获取消息,并且事先不知道这些消息是否持久,那么可以使用 GMO 选项 MQGMO_SYNCPOINT_IF_PERSISTENT。