【问题标题】:ActiveMQ does not actually respect memory limitsActiveMQ 实际上并不尊重内存限制
【发布时间】:2019-06-22 06:09:47
【问题描述】:

我正在尝试将 ActiveMQ 设置为使用内存限制和生产者流控制,以便在内存不足时尝试发送消息时看不到挂起行为。我遵循了Producer Flow ControlMy producer blocksConnection Configuration URI 的文档,但运气不佳。

我遇到的问题是这些设置实际上并没有得到适当的尊重。

我的 ActiveMQ 代理在我的 Spring 配置中是这样设置的(我已经稍微清理了一下,所以可能不是 100% 有效的 Spring 配置):

<bean id="broker" class="org.apache.activemq.broker.BrokerService"
    init-method="start">
    <property name="brokerName" value="broker" />
    <property name="persistent" value="false" />
    <property name="useJmx" value="true" />
    <property name="managementContext" ref="mgmtContext" />
    <property name="transportConnectorURIs">
        <list>
            tcp://localhost:1234?jms.prefetchPolicy.queuePrefetch=0&jms.useAsyncSend=false&jms.alwaysSyncSend=true
        </list>
    </property>
        <property name="destinations">
            <list>
                <bean class="org.apache.activemq.command.ActiveMQQueue">
                    <property name="physicalName" value="requests"></property>
                </bean>
                <bean class="org.apache.activemq.command.ActiveMQQueue">
                    <property name="physicalName" value="responses"></property>
                </bean>
            </list>
    </property>
</bean>

然后在我的一个代码初始化方法中,我设置了以下内容:

broker.getSystemUsage().setSendFailIfNoSpace(true);
broker.getSystemUsage().setSendFailIfNoSpaceAfterTimeout(5000);

// Limit memory usage to 10MB
broker.getSystemUsage().getMemoryUsage().setLimit(10 * 1024 * 1024);

然而,当我运行我的代码时,我仍然在日志中看到如下内容:

2013-Mar-14 14:47:31.538 GMT-06:00 DEBUG [ActiveMQ Transport: tcp:///127.0.0.1:45846@18086] [org.apache.activemq.usage.Usage:fireEvent] [Usage.java:245] [] [] [] - Main:memory: usage change from: 5640% of available memory, to: 0% of available memory

所以 ActiveMQ 似乎公然无视设置的内存限制。

如果您将足够大的消息放入队列,我仍然会看到可能发生的阻塞行为,如果我将非常大的消息放入队列,甚至会出现 OOM 错误。

如何可靠地配置 ActiveMQ 以限制其内存使用量。

【问题讨论】:

    标签: java jms activemq


    【解决方案1】:

    对于希望以编程方式管理代理限制的任何人,以下是一个示例:

        @Bean
        public BrokerService broker()
                throws Exception {
            final BrokerService broker = new BrokerService();
            broker.addConnector("tcp://localhost:61616");
            broker.addConnector("vm://localhost");
            broker.setPersistent(false);
            broker.getConsumerSystemUsage().getMemoryUsage().setLimit(100 * 1024);
            broker.getConsumerSystemUsage().getStoreUsage().setLimit(1024 * 1024);
            broker.getConsumerSystemUsage().getTempUsage().setLimit(100 * 1024);
            return broker;
        }
    

    感谢这篇文章的起点: How to set ActiveMQ port in Spring Boot?

    【讨论】:

      【解决方案2】:

      您是否尝试过直接使用 xml 文件配置代理? 你可以这样做(摘自official Java example):

      BrokerService 代理 = BrokerFactory.createBroker(configUrl);

      稍后我会尝试获取一个正在运行的 Spring 示例

      【讨论】:

        【解决方案3】:

        我已经尝试过了,但我无法解决我正在寻找的东西,但我终于得到了下面的链接,它有完整的信息

        http://blogs.sourceallies.com/2014/10/activemq-memory-tuning/

        感谢上面的帖子,我得到了解决方案。 上面的线程有大量的信息。 我已将 activemq.xml 更改如下

        <systemUsage>
                    <systemUsage>
                        <memoryUsage>
                            <memoryUsage limit="2048 mb"/>
                            <!--Earlier it use to be 
                            <memoryUsage limit="64 mb"/>
                            -->
                        </memoryUsage>
                        <storeUsage>
                            <storeUsage limit="100 gb"/>
                        </storeUsage>
                        <tempUsage>
                            <tempUsage limit="50 gb"/>
                        </tempUsage>
                    </systemUsage>
                </systemUsage>
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2011-10-03
          • 1970-01-01
          • 2019-01-17
          • 2021-12-21
          相关资源
          最近更新 更多