ApsaraMQ for RocketMQ ofrece dos tipos de consumidor: Push consumer y Simple consumer. Cada tipo gestiona la obtención de mensajes, la concurrencia y los reintentos de forma distinta. Elija el tipo que se ajuste a su modelo de procesamiento y a sus requisitos de confiabilidad.
Qué tipo de consumidor utilizar
|
Escenario |
Tipo recomendado |
Razón |
|
Tiempo de procesamiento predecible, sin hilos personalizados |
Push consumer |
El SDK gestiona la obtención de mensajes, la concurrencia y los reintentos. Registre un listener, procese cada mensaje y devuelva el resultado. |
|
Tiempo de procesamiento variable, flujos de trabajo personalizados |
Simple consumer |
Su aplicación controla cuándo obtener los mensajes, cómo distribuirlos entre los hilos y cuándo confirmar la finalización del procesamiento. |
Cambiar el tipo de consumidor no afecta los recursos existentes de ApsaraMQ for RocketMQ ni el procesamiento del negocio.
Etapas del procesamiento de mensajes
Ambos tipos de consumidor siguen un ciclo de vida de tres etapas:
Recepción: obtención de mensajes del servidor.
Procesamiento: ejecución de la lógica de negocio para cada mensaje.
Confirmación: notificación del resultado (éxito o fallo) al servidor.

Los dos tipos difieren en la forma en que manejan cada etapa:
|
Función |
Push consumer |
Simple consumer |
|
Interfaz |
Callback de listener: implemente la lógica dentro del listener y devuelva un resultado |
La aplicación invoca operaciones de API para recibir, procesar y confirmar mensajes |
|
Concurrencia |
Gestionada por el SDK |
Gestionada por la aplicación |
|
Flexibilidad |
Altamente encapsulado, menor flexibilidad |
Operaciones atómicas, altamente personalizable |
|
Más indicado para |
Consumo estándar con tiempo de procesamiento predecible |
Flujos de trabajo personalizados, distribución asíncrona o consumo por lotes |
|
Clases del SDK |
|
|
Push consumers
Un Push consumer encapsula la lógica de obtención de mensajes, gestión de hilos y reintentos. Registre un message listener durante la inicialización y el SDK se encargará del resto.
Funcionamiento
El SDK utiliza internamente un modelo de hilos Reactor:
Un hilo integrado de long-polling obtiene mensajes del servidor de manera asíncrona.
Los mensajes se colocan en una cola de caché interna.
El SDK distribuye los mensajes a los hilos de consumo, los cuales invocan su listener.

Resultados del listener
El message listener debe devolver uno de los siguientes resultados:
|
Resultado |
Constante del SDK de Java |
Comportamiento |
|
Éxito |
|
El servidor actualiza el progreso de consumo. |
|
Fallo |
|
El sistema reintenta según la PushConsumer retry policy. |
|
Excepción lanzada |
(tratado como fallo) |
Mismo comportamiento de reintento que un fallo explícito. |
Comportamiento ante tiempo de espera agotado
Si la lógica de procesamiento se bloquea e impide completar el mensaje dentro del tiempo permitido, el SDK envía forzosamente un resultado de fallo y gestiona el mensaje según la política de reintentos.
Un tiempo de espera agotado provoca que el SDK envíe un resultado de fallo, pero es posible que el hilo de procesamiento actual no responda a la interrupción y continúe ejecutándose.
Restricciones de confiabilidad
El Push consumer determina el éxito o el fallo estrictamente a partir del valor de retorno del listener. Para preservar esta garantía:
Procese de forma síncrona. Complete todo el procesamiento antes de devolver el resultado.
No redistribuya mensajes. No transfiera mensajes a otros hilos ni devuelva un resultado antes de que dichos hilos finalicen.
Si el listener devuelve éxito antes de que finalice el procesamiento y este falla posteriormente, el servidor considera el mensaje como consumido y no lo reintenta.
Entrega ordenada de mensajes
Cuando un grupo de consumidores utiliza el modo de consumo ordenado, el Push consumer invoca el listener respetando estrictamente el orden de los mensajes, sin necesidad de configuración adicional. Para más información, consulte Ordered messages.
La entrega ordenada requiere procesamiento síncrono. Una distribución asíncrona personalizada dentro del listener anula la garantía de orden.
Cuándo utilizar Push consumers
Los Push consumers son más adecuados cuando:
El tiempo de procesamiento es predecible. Las duraciones impredecibles provocan tiempos de espera agotados frecuentes, lo que genera mensajes duplicados debido a los reintentos.
El consumo estándar es suficiente. El SDK controla el modelo de hilos y entrega mensajes con el máximo rendimiento. Esto simplifica el desarrollo, pero no admite procesamiento asíncrono ni control personalizado de la tasa de transferencia.
Clases del SDK
ApsaraMQ for RocketMQ proporciona dos clases del SDK para Push consumers:
**
PushConsumer**: consume mensajes de temas estándar (no Lite).**
LitePushConsumer**: consume mensajes de temas de tipo Lite, con control de consumo a nivel de granularidad del tema Lite.
Ejemplo de PushConsumer
// Consume normal messages with PushConsumer
ClientServiceProvider provider = ClientServiceProvider.loadService();
String topic = "<your-topic>";
FilterExpression filterExpression = new FilterExpression("<your-filter-tag>", FilterExpressionType.TAG);
PushConsumer pushConsumer = provider.newPushConsumerBuilder()
// Set the consumer group
.setConsumerGroup("<your-consumer-group>")
// Set the access endpoint
.setClientConfiguration(ClientConfiguration.newBuilder().setEndpoints("<your-endpoint>").build())
// Bind the subscription
.setSubscriptionExpressions(Collections.singletonMap(topic, filterExpression))
// Register the message listener
.setMessageListener(new MessageListener() {
@Override
public ConsumeResult consume(MessageView messageView) {
// Process the message and return the result
return ConsumeResult.SUCCESS;
}
})
.build();
Reemplace los siguientes marcadores de posición con sus valores reales:
|
Marcador de posición |
Descripción |
Ejemplo |
|
|
Nombre del tema |
order-events |
|
|
Etiqueta de mensaje para filtrado |
payment |
|
|
Nombre del grupo de consumidores |
order-service-group |
|
|
Endpoint de acceso al servidor |
-- |
Ejemplo de LitePushConsumer
// Consume normal messages with LitePushConsumer
ClientServiceProvider provider = ClientServiceProvider.loadService();
LitePushConsumer litePushConsumer = provider.newLitePushConsumerBuilder()
// Set the access endpoint
.setClientConfiguration(ClientConfiguration.newBuilder().setEndpoints("<your-endpoint>").build())
// Set the topic
.bindTopic("<your-topic>")
// Set the consumer group
.setConsumerGroup("<your-consumer-group>")
// Register the message listener
.setMessageListener(messageView -> {
// Process the message and return the result
return ConsumeResult.SUCCESS;
})
.build();
// Subscribe to Lite topics
litePushConsumer.subscribeLite("<your-lite-topic-1>");
litePushConsumer.subscribeLite("<your-lite-topic-2>");
Simple consumers
Un Simple consumer proporciona operaciones de API atómicas para el procesamiento de mensajes. Su aplicación controla directamente la obtención de mensajes, la gestión de hilos y la confirmación.
Funcionamiento
Invoque
ReceiveMessagepara obtener un lote de mensajes del servidor.Distribuya los mensajes a sus hilos de negocio para su procesamiento.
Invoque
AckMessagepor cada mensaje procesado correctamente.
Si el procesamiento falla, no envíe una confirmación. El mensaje vuelve a estar disponible después de que expire la duración de invisibilidad del mensaje, lo que desencadena un reintento. Para más información, consulte SimpleConsumer retry policy.
Operaciones de API
|
Operación |
Propósito |
Parámetros clave |
|
|
Obtener mensajes del servidor |
Tamaño del lote: número de mensajes por solicitud. Duración de invisibilidad del mensaje: tiempo máximo de procesamiento antes de que el mensaje se vuelva a entregar. |
|
|
Confirmar consumo exitoso |
Ninguna |
|
|
Extender el tiempo de procesamiento de un mensaje ya recibido |
Duración de invisibilidad del mensaje: nuevo valor, utilizado generalmente cuando el procesamiento tarda más de lo previsto inicialmente. |
El servidor utiliza almacenamiento distribuido, por lo que ReceiveMessage puede devolver un resultado vacío incluso si existen mensajes. Para manejar esta situación, invoque nuevamente ReceiveMessage o aumente la concurrencia de las llamadas.
Gestión de fallos
La siguiente tabla describe cómo afectan los distintos escenarios de fallo a la entrega de mensajes:
|
Escenario de fallo |
Comportamiento |
|
Fallo en el procesamiento (sin ACK enviado) |
El mensaje vuelve a ser visible después de que expire la duración de invisibilidad. El servidor lo vuelve a entregar para reintento. |
|
El procesamiento excede la duración de invisibilidad |
Igual que sin ACK: el mensaje se vuelve visible y se vuelve a entregar. Utilice |
|
El consumidor falla antes de enviar el ACK |
El mensaje se vuelve a entregar después de que expire la duración de invisibilidad. |
Entrega ordenada de mensajes
Un Simple consumer procesa ordered messages en el orden de almacenamiento. Para un grupo de mensajes que deben mantener su secuencia, no se puede obtener el siguiente mensaje hasta que se haya procesado el anterior.
Cuándo utilizar Simple consumers
Los Simple consumers son más adecuados cuando:
El tiempo de procesamiento es impredecible. Especifique una duración inicial de invisibilidad del mensaje al invocar
ReceiveMessagey extiéndala conChangeInvisibleDurationsi es necesario.Se requieren flujos de trabajo personalizados. El SDK no impone ningún modelo de hilos; implemente distribución asíncrona, consumo por lotes o cualquier patrón personalizado.
El control de la tasa de transferencia es importante. Su código decide cuándo y con qué frecuencia invocar
ReceiveMessage, lo que proporciona control directo sobre el rendimiento.
Clase del SDK
ApsaraMQ for RocketMQ proporciona una clase del SDK para Simple consumers: SimpleConsumer. Esta clase no puede consumir mensajes de temas Lite.
Ejemplo de SimpleConsumer
// Consume normal messages with SimpleConsumer
ClientServiceProvider provider = ClientServiceProvider.loadService();
String topic = "<your-topic>";
FilterExpression filterExpression = new FilterExpression("<your-filter-tag>", FilterExpressionType.TAG);
SimpleConsumer simpleConsumer = provider.newSimpleConsumerBuilder()
// Set the consumer group
.setConsumerGroup("<your-consumer-group>")
// Set the access endpoint
.setClientConfiguration(ClientConfiguration.newBuilder().setEndpoints("<your-endpoint>").build())
// Bind the subscription
.setSubscriptionExpressions(Collections.singletonMap(topic, filterExpression))
.build();
try {
// Pull up to 10 messages, wait up to 30 seconds
List<MessageView> messageViewList = simpleConsumer.receive(10, Duration.ofSeconds(30));
messageViewList.forEach(messageView -> {
System.out.println(messageView);
// Acknowledge each message after successful processing
try {
simpleConsumer.ack(messageView);
} catch (ClientException e) {
e.printStackTrace();
}
});
} catch (ClientException e) {
// Handle failures such as throttling, then retry the receive call
e.printStackTrace();
}
Mejores prácticas
Control del tiempo de procesamiento para Push consumers
Mantenga el procesamiento de mensajes dentro del umbral de tiempo de espera. Los tiempos de espera agotados frecuentes causan reintentos innecesarios y mensajes duplicados. Si su aplicación maneja habitualmente tareas de larga duración, cambie a un Simple consumer y establezca una duración adecuada de invisibilidad del mensaje.
Migración de LitePullConsumer a SimpleConsumer
LitePullConsumer era un tipo de consumidor en el SDK Remoting de Apache RocketMQ 4.x. Se eliminó en el SDK gRPC 5.x, y los SDK 5.x de Go, Java y Python no incluyen este tipo.
Si anteriormente utilizaba LitePullConsumer para consumo basado en extracción, migre a **SimpleConsumer** después de actualizar al SDK 5.x. SimpleConsumer proporciona las siguientes operaciones:
ReceiveMessage: obtiene mensajes del servidor bajo demanda.AckMessage: confirma el consumo exitoso.ChangeInvisibleDuration: modifica la duración de invisibilidad del mensaje para controlar el intervalo de reintentos.
En el SDK de Go, los métodos correspondientes son Receive y Ack. En el SDK de Java, los métodos correspondientes son receive y ack.