3.异步、同步生产消费、批量处理
同步
生产
/**
* 同步-生产消息
* @param msg
* @throws PulsarClientException
*/
@GetMapping("/model/sendMsgBySync")
public MessageId sendMsgBySync(String msg) throws PulsarClientException {
PulsarClient pulsarFactory = pulsarConf.pulsarFactory();
Producer<byte[]> producer = pulsarFactory.newProducer()
.topic("my-topic")
.create();
// 然后你就可以发送消息到指定的broker 和topic上:
return producer.send(msg.getBytes());
}
消费
/**
* 手动执行同步获取消息
* @throws PulsarClientException
*/
@GetMapping("/model/comsumerBySync")
public void comsumerByArtificialBySync() throws PulsarClientException {
PulsarClient pulsarFactory = pulsarConf.pulsarFactory();
Consumer<byte[]> consumer = pulsarFactory.newConsumer()
.topic("my-topic")
.subscriptionName("my-subscription")
.subscribe();
Message<byte[]> receive = consumer.receive();
System.out.println(new String(receive.getData()));
consumer.acknowledge(receive);//确认消息被消费
consumer.close();
}
异步
生产
/**
* 异步-生产消息
* @param msg
* @throws PulsarClientException
*/
@GetMapping("/model/sendMsgAsync")
public void sendMsgAsync(String msg) throws PulsarClientException {
PulsarClient pulsarFactory = pulsarConf.pulsarFactory();
Producer<byte[]> producer = pulsarFactory.newProducer()
.topic("my-topic")
.create();
// 然后你就可以发送消息到指定的broker 和topic上:
producer.sendAsync(msg.getBytes()).thenAccept(msgId -> {
System.out.println("Message with ID " + msgId + " successfully sent");
});
}
消费
/**
* 手动执行异步获取消息
* @throws PulsarClientException
*/
@GetMapping("/model/comsumerByASync")
public void comsumerByArtificialByASync() throws PulsarClientException {
PulsarClient pulsarFactory = pulsarConf.pulsarFactory();
Consumer<byte[]> consumer = pulsarFactory.newConsumer()
.topic("my-topic")
.subscriptionName("my-subscription")
.subscribe();
CompletableFuture<Message<byte[]>> asyncMessage = consumer.receiveAsync();
asyncMessage.thenAccept(message -> {
System.out.println(new String(message.getData()));
try {
consumer.acknowledge(message.getMessageId());
consumer.close();
} catch (PulsarClientException e) {
e.printStackTrace();
}
});
}
批量处理
生产
Pulsar生产者默认用的是"消息块"来实现批量发送,但没有想到应用场景,先挂个链接,有个印象,以后遇到了再看
消费
/**
* 批量消费消息
* 累计消息数量|累计消息大小|指定时间拉取一次满足其一即执行
* @throws PulsarClientException
*/
@GetMapping("/model/comsumerByBatch")
public void comsumerByBatch() throws PulsarClientException {
PulsarClient pulsarFactory = pulsarConf.pulsarFactory();
Consumer<byte[]> consumer = pulsarFactory.newConsumer()
.topic("my-topic")
.subscriptionName("my-subscription")
.batchReceivePolicy(BatchReceivePolicy.builder()
.maxNumMessages(5) //累计消息数量,默认-1,不限制
.maxNumBytes(1024 * 1024)//累计消息大小,默认 10 * 1024 * 1024
.timeout(200, TimeUnit.MILLISECONDS)//指定时间拉取一次,默认 100
.build())
.subscribe();
Messages<byte[]> messages = consumer.batchReceive();
// consumer.batchReceiveAsync();//异步同理
System.out.println("本次接收"+messages.size()+"条");
for (Message<byte[]> message : messages) {
System.out.println(new String(message.getData()));
}
consumer.acknowledge(messages);//确认消息被消费
consumer.close();
}
取消消费
假设,消费者调用acknowledge消费消息后程序报错,数据回滚,但Pulsar不知道回滚了,导致数据无法再次消费,所以需要回滚消费标识
/**
* 取消消费
* @throws PulsarClientException
*/
@GetMapping("negativeAcknowledgement")
public void negativeAcknowledgement() throws PulsarClientException {
PulsarClient pulsarFactory = pulsarConf.pulsarFactory();
Consumer<byte[]> consumer = pulsarFactory.newConsumer()
.topic("my-topic")
.subscriptionName("my-subscription")
.subscribe();
Message<byte[]> receive = consumer.receive();
MessageId messageId = receive.getMessageId();
try {
System.out.println(new String(receive.getData()));
consumer.acknowledge(receive);//确认消息被消费
} catch (PulsarClientException e) {
consumer.negativeAcknowledge(messageId);//消息取消消费,会被重新消费
e.printStackTrace();
}
consumer.close();
}