我有一个系统,对它所做的事情有严格的“一次和一次”的要求。它是一个具有中间件的事件驱动系统,不能保证一次和一次消息传递(如果对这是否是重传有疑问的话,它将将任何给定的消息标记为“重新传递”)。“一次和唯一一次”处理实质上可以归结为我们的核心域对象的状态,即它是一个相当标准的设置,其中.
arrive
3最终必须命中一个数据库(书籍和记录),4可以采取多种形式,但都是某种形式的消息传递给外部系统。还有各种各样的其他流,但它们都归结为这种处理方式。所有消息都将在核心域对象的单个实例上运行,因此处理可以将该实例固定在单个jvm上。
我的Q很笼统,可能太笼统了,但我还是会问的。也就是说,在保持所需的保证的同时,可以采用什么策略/模式来提高吞吐量?或者,会导致性能下降的主要问题是什么?
例如,一种思路是避免在关键路径上的任何持久性,这可以归结为如何保持内存状态的一致性,而不需要从数据库中刷新。
您可以假设可以通过一些分区策略来扩展,但是这个方面超出了q的范围。Q是关于如何在这样的系统中增加单个节点的吞吐量。
注意,这是一个大型企业环境中的java/oracle,所以小众硬件(例如Exadata&Friend或一些漂亮的网络工具包)是可以的。
发布于 2011-11-09 09:23:05
这在很大程度上取决于您需要什么样的保证,取决于如何处理失败。您可以使用平面日志文件和/或冗余服务器来实现每秒100万以上的消息传递速率。
你需要的主要模式是演员模式。要提高吞吐量,您需要能够透明地对数据进行批处理,作为设计的一部分。就我个人而言,我喜欢使用直接ByteBuffers (大部分数据不在堆上),因为它们是处理大量数据的一种轻量级方法,可以轻松地复制和读写NIO通道。我已经编写了自己的解析/日志库,用于减少gc的输入/输出。
另一个有用的策略是预先分配和回收对象。这可以帮助消除GC的风险,因为它不创建垃圾(或者只创建非常小的数量,可以每天收集一次)。
诀窍是在您的持久性保证得到满足之前,不要发布处理的结果。(最简单的方法是没有任何担保,说最后几个交易可能会丢失,并将手工处理)
影响性能的主要因素有:
asynchronous.
发布于 2011-11-09 16:39:37
这“相当”容易,“只是”使您的操作幂等,并破坏所有操作。
https://stackoverflow.com/questions/8058916
复制相似问题