redimensionar icon adjust java spring jms activemq spring-jms

java - icon - JMS rendimiento del productor con la primavera



resize image java jlabel (4)

Creé una simple simulación de consumidor productor basada en spring, jms y activemq. Intento alcanzar un alto rendimiento de ambos lados, productores y consumidores.

Ajustes de conexión:

<tx:annotation-driven /> <bean id="transactionManager" class="org.springframework.jms.connection.JmsTransactionManager"> <property name="connectionFactory" ref="connectionFactory" /> </bean> <amq:connectionFactory id="amqConnectionFactory" brokerURL="failover:(tcp://${broker.url}:61616)" /> <bean id="connectionFactory" class="org.springframework.jms.connection.CachingConnectionFactory"> <property name="targetConnectionFactory" ref="amqConnectionFactory" /> </bean> <amq:queue id="queue" physicalName="queue" /> <beans:bean id="jsonMessageConverter" class="XXXXX.converter.JsonMessageConverter" />

Configuración del consumidor:

<jms:listener-container concurrency="10" acknowledge="auto" prefetch="1" message-converter="jsonMessageConverter" transaction-manager="transactionManager" > <jms:listener id="queueListener_1" destination="ooIntegrationQueue" ref="myMessageListenerAdapter" /> </jms:listener-container> <beans:bean id="myMessageListenerAdapter" class="org.springframework.jms.listener.adapter.MessageListenerAdapter" > <beans:property name="delegate" ref="consumer"/> </beans:bean> <beans:bean id="consumer" class="XXX.ConsumerImpl"/>

Configuración del productor:

<beans:bean id="jmsTemplate" class="org.springframework.jms.core.JmsTemplate" p:connectionFactory-ref="connectionFactory" p:messageConverter-ref="jsonMessageConverter" p:defaultDestination-ref="ooIntegrationQueue" p:sessionTransacted="true" />

comenzando con el consumidor, logré consumir unos 25 mensajes por segundo, lo cual es extremadamente lento, descubrí que el cuello de botella era el hecho de que estoy usando transacciones, después de buscar en Google por un tiempo, y jugando con las configuraciones, descubrí que después de autowiring el DefaultMessageListenerContainer y cambiar el nivel de caché a

listenerContainer.setCacheLevelName("CACHE_SESSION")

Mi rendimiento aumenta a aproximadamente 1500 mensajes por segundo mientras sigo teniendo transacciones.

Mi problema es ahora con el productor, que todavía está bloqueado en aproximadamente 25 operaciones por segundo, mi prueba de productor es simple:

int numOfMessages = getNumberOfMessages(); double startTime = System.currentTimeMillis(); for (int i = 1; i <= numOfMessages; i++) { jmsTemplate.convertAndSend("HelloWorld" + i); } double endTime = System.currentTimeMillis(); double totalTime=(endTime-startTime)/1000; System.out.println("Time - "+totalTime+" seconds"); System.out.println("EPS - "+numOfMessages/totalTime);

Me pregunto cómo llegar a actuaciones similares con el productor, ya que ahora bloquea todo el sistema.


¿Cuál es el modo de entrega predeterminado para ActiveMQ? ¿Es una cola persistente? Si es así, ¿cómo se configura? ¿Qué tan remoto es el corredor? Estas respuestas determinarán el costo básico del envío a la cola al responder cuánto tiempo le toma al servidor aceptar el envío (es decir, el costo potencial de la red RTT + de persistir el mensaje en el disco de forma sincrónica).

La otra posibilidad es que en realidad está creando una nueva conexión, sesión y productor de mensajes en cada envío. Esto es bastante costoso para decir lo menos. Valdrá la pena confirmar si esto está sucediendo (por ejemplo, agregar el registro de depuración a Spring, verificar la consola de administración de amq para determinar la rotación de la conexión) o no como una comprobación de seguridad básica. Por su aspecto, CachingConnectionFactory debe almacenar en caché una sola sesión y un productor de mensajes de forma predeterminada, y convertAndSend debe cerrar la sesión que obtiene después de enviar, lo que da como resultado que se devuelva esa sesión en caché al grupo. Esto debería significar que es relativamente rápido (spring jms pasa por una gran cantidad de códigos para enviar un mensaje) para obtener la sesión en caché en el próximo envío.


Intente cambiar el método de reconocimiento de AUTO a CLIENT_ACKNOWLEDGE. Para más información mira la Specification .


JMSTemplate realiza un recorrido por ConnectionFactiory -> Connection -> Session -> MessageProducer, cerrando cada objeto después de cada envío. Para solucionar esto, envuelva su bean amqConnectionFactory con un org.apache.activemq.pool.PooledConnectionFactory, y use eso debajo de la plantilla en lugar de un CachingConnectionFactory.


Lo siento si esta respuesta llega tarde para ayudar al cartel original. Recientemente he investigado el rendimiento de JmsTemplate . Incluso con los mismos modos de entrega y confirmación, el código JMS nativo parecía mucho más rápido que JmsTemplate . El problema resultó ser que ActiveMQ general es el envío asíncrono, pero cuando usa JmsTemplate , en su lugar usa el envío de sincronización. Esto reduce dramáticamente el rendimiento. Puede establecer la propiedad useAsyncSend ActiveMQConnectionFactory en true para forzar el envío asíncrono. Más detalles aquí: JmsTemplate no es malo