跳到主要内容

线程安全性

PubSub+ 消息 API 确保某些 API 元素是线程安全的,而其他元素则由应用程序开发人员负责。下表列出了每个 API 元素的线程安全性责任归属:

PubSub+ API 的元素线程安全性
API 内置
线程安全性应用程序开发者的
责任
------
上下文(Contexts)img
会话(Sessions)
流(Flows)
消息(Messages)
事务性会话(Transacted Sessions)
事务性流(Transacted Flows)

上下文、会话和流:线程安全

您的企业可能需要多个上下文来组织应用程序与事件代理之间的通信。同样,您的应用程序可能在一个会话中使用多个发布者或接收者,这需要多线程支持。为了确保应用程序在运行过程中能够依赖确定的 API 结果,消息 API 保证您创建的所有上下文、会话和流都是线程安全的。消息 API 使用两种内置机制来确保上下文、会话和流(这些支持保证消息传递)保持线程安全:

PubSub+ 消息 API 中的所有回调都在同一个内部上下文线程上发生,这使得它们是线程安全的。

互斥锁(Mutex)锚点

为了确保线程安全,消息 API 使用互斥锁(mutexes)来限制代码段仅由一个线程执行。当该线程执行完该代码段后,代码段会被解锁,其他线程可以访问它。互斥锁的使用确保了在任何时刻只有一个线程可以访问多个线程共享的资源。

img

序列化锚点

有时线程安全可能需要跨越数百甚至数千行代码。为了避免锁定大量代码段(这可能导致程序阻塞并失去性能),消息 API 使用序列化。通过序列化,特定操作的任务被安排在某个线程上,以确保它们按特定顺序执行,并防止它们同时运行。这确保了这些任务按顺序运行,不会相互冲突。

img

由于序列化是在消息 API 的上下文线程上完成的,因此您无需在应用程序中实现它。

这两种机制的结合确保了在多线程的企业应用程序中使用上下文、流和会话时,不会出现不确定的结果或意外行为。


消息:开发者的责任

消息 API 不保证消息是线程安全的,但这更多地与事件流的特性有关,而不是数据稳定性问题。我们建议您在单个线程上实现单个消息的处理。这可以确保每条消息的负载不会受到竞争条件或线程安全问题的影响,从而避免出现不确定的结果。


事务性会话和事务性流:开发者的责任

PubSub+ 消息 API 支持本地事务(JMS 除外,它还支持分布式事务),由于本地事务是基于 JMS 事务建模的,因此它们遵循 JMS 协议。JMS 协议要求本地事务(包括事务性流和事务性会话)由单个线程处理。这是因为事务性会话没有明确的开始或结束,而事务的完成需要一个提交调用。事务提交后,即视为完成。此时,事务消息被发送或接收,一个新的事务开始。这意味着事务性会话或流的所有处理必须由单个线程进行处理和控制,类似于消息处理的方式。尽管这意味着事务性会话和事务性流在技术上不是线程安全的,但它们以单线程方式运行,不会带来任何线程安全风险。