主要是生产者产生消息的时候发生异常进行回滚
生产者代码:
package cn.nxcoder.rabbit.shiwu;
import com.rabbitmq.client.ConnectionFactory;
import com.rabbitmq.client.Connection;
import com.rabbitmq.client.Channel;
public class SendShiwu {
private final static String QUEUE_NAME = "shiwu";
public static void main(String[] argv) throws Exception {
ConnectionFactory factory = new ConnectionFactory();
factory.setHost("101.200.55.12");
factory.setUsername("admin");
factory.setPassword("xiyouyan");
Connection connection = factory.newConnection();
Channel channel = connection.createChannel();
try {
channel.queueDeclare(QUEUE_NAME, false, false, false, null);
channel.txSelect();
String message = "这是测试消息发送失败事务回滚..........发送的消息";
//下面的注释掉能正常发送。不注释不能正常发送,会进行回滚提交
int a = 1 / 0;
channel.basicPublish("", QUEUE_NAME, null, message.getBytes());
channel.txCommit();
System.out.println(" [x] Sent '" + message + "'");
} catch (Exception e) {
channel.txRollback();
System.out.println("消息发送的时候发送异常,已经进行了回滚");
} finally {
channel.close();
connection.close();
System.out.println("发送者连接已关闭");
}
}
}
消费者
package cn.nxcoder.rabbit.shiwu;
import com.rabbitmq.client.*;
import java.io.IOException;
public class ReceiveShiwu {
private final static String QUEUE_NAME = "shiwu";
public static void main(String[] argv) throws Exception {
ConnectionFactory factory = new ConnectionFactory();
factory.setHost("101.200.55.12");
factory.setUsername("admin");
factory.setPassword("xiyouyan");
Connection connection = factory.newConnection();
Channel channel = connection.createChannel();
channel.queueDeclare(QUEUE_NAME, false, false, false, null);
System.out.println(" [*] Waiting for messages. To exit press CTRL+C");
/***
* 下面代码的作用是让程序一直运行,除非CTRL+C或者自己主动中断,为消息提供异步接收支持
* 因为生产者会异步地向我们发送消息,所以我们以对象的形式提供一个回调,它将缓冲消息,直到我们准备好使用它们
*/
DeliverCallback deliverCallback = (consumerTag, delivery) -> {
String message = new String(delivery.getBody(), "UTF-8");
System.out.println(" [x] Received '" + message + "'");
};
//设置回调
boolean autoAck = true;
channel.basicConsume(QUEUE_NAME, autoAck, new DefaultConsumer(channel) {
@Override
public void handleDelivery(String consumerTag,
Envelope envelope,
AMQP.BasicProperties properties,
byte[] body)
throws IOException {
System.out.println("接收到的消息是:" + new String(body, "utf-8"));
}
});
}
}
正常发送和接收:
//生产者
[x] Sent '这是测试消息发送失败事务回滚..........发送的消息'
发送者连接已关闭
//消费者
[*] Waiting for messages. To exit press CTRL+C
接收到的消息是:这是测试消息发送失败事务回滚..........发送的消息
//异常发送生产者
消息发送的时候发送异常,已经进行了回滚
发送者连接已关闭
//异常消费者
[*] Waiting for messages. To exit press CTRL+C
缺点
降低吞吐量