【RabbitMQ】08 深入部分P1 可靠性投递
1、消息投递确认
这里的代码延用了06的东西:
https://www.cnblogs.com/mindzone/p/15374684.html
删除之前的整合案例,重新写了一份案例的队列和交换机配置
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:rabbit="http://www.springframework.org/schema/rabbit"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
https://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/rabbit
http://www.springframework.org/schema/rabbit/spring-rabbit.xsd">
<!--加载配置文件-->
<context:property-placeholder location="classpath:rabbitmq.properties"/> <!-- 定义rabbitmq connectionFactory publisher-confirms="true" 消息发送可确认
publisher-returns="true"
-->
<rabbit:connection-factory id="connectionFactory" host="${rabbitmq.host}"
port="${rabbitmq.port}"
username="${rabbitmq.username}"
password="${rabbitmq.password}"
virtual-host="${rabbitmq.virtual-host}"
publisher-confirms="true"
publisher-returns="true"
/>
<!--定义管理交换机、队列-->
<rabbit:admin connection-factory="connectionFactory"/> <!--定义rabbitTemplate对象操作可以在代码中方便发送消息-->
<rabbit:template id="rabbitTemplate" connection-factory="connectionFactory"/> <!-- 消息可靠性投递 -->
<rabbit:queue id="confirm-test-queue" name="confirm-test-queue" />
<rabbit:direct-exchange name="confirm-test-exchange" >
<rabbit:bindings>
<rabbit:binding queue="confirm-test-queue" key="confirm" />
</rabbit:bindings>
</rabbit:direct-exchange> </beans>
测试类:
package cn.dzz; import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.amqp.rabbit.connection.CorrelationData;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; @RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath*:producer-config.xml")
public class SpringProducerTest { @Autowired
private RabbitTemplate rabbitTemplate; /**
* 消息送出可靠性测试
* 1、xml配置数据连接工厂开启消息可确认设置 √
* 2、rabbitTemplate对象定义回调函数
*/
@Test
public void sendingReliableTest() { /**
* CorrelationData correlationData相关配置信息
* boolean ack 来自交换机收到消息的确认参数 true收到了 false没收到
* String cause 失败的原因信息 发送成功了就没有失败原因 case为null
*/
rabbitTemplate.setConfirmCallback((correlationData, ack, cause) -> {
System.out.println("确认消息真的从生产者服务发送到了RabbitMQ中间件这里, 然后这个周期的时刻需要做的什么事情 。。。。");
if (ack) {
System.out.println("rabbitMQ收到消息了 " + cause);
} else {
System.out.println("rabbitMQ没收到消息 : cause by " + cause);
// 如果没收到就需要做对应的处理逻辑
}
});
rabbitTemplate.convertAndSend("confirm-test-exchange", "confirm", " 发送一条消息以测试confirm回调。。。。");
}
}
可靠投递确认就是设置两样东西
1、连接工厂开启确认项配置
2、模板对象重写确认回调函数
正常编写配置,执行结果肯定是消息发送正常
输出信息:
"C:\Program Files (x86)\Java\jdk1.8.0_291\bin\java.exe" -ea -Didea.test.cyclic.buffer.size=1048576 "-javaagent:C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\lib\idea_rt.jar=51932:C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\bin" -Dfile.encoding=UTF-8 -classpath "C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\lib\idea_rt.jar;C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\plugins\junit\lib\junit5-rt.jar;C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\plugins\junit\lib\junit-rt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\charsets.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\deploy.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\access-bridge-32.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\cldrdata.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\dnsns.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\jaccess.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\jfxrt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\localedata.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\nashorn.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunec.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunjce_provider.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunmscapi.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunpkcs11.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\zipfs.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\javaws.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jce.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jfr.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jfxswt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jsse.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\management-agent.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\plugin.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\resources.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\rt.jar;C:\Users\Administrator\IdeaProjects\RabbitMQ\Spring-RabbitMQ-Producer\target\test-classes;C:\Users\Administrator\IdeaProjects\RabbitMQ\Spring-RabbitMQ-Producer\target\classes;C:\Users\Administrator\.m2\repository\org\springframework\spring-context\5.3.10\spring-context-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-aop\5.3.10\spring-aop-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-beans\5.3.10\spring-beans-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-core\5.3.10\spring-core-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-jcl\5.3.10\spring-jcl-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-expression\5.3.10\spring-expression-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\amqp\spring-rabbit\2.1.8.RELEASE\spring-rabbit-2.1.8.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\amqp\spring-amqp\2.1.8.RELEASE\spring-amqp-2.1.8.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\retry\spring-retry\1.2.4.RELEASE\spring-retry-1.2.4.RELEASE.jar;C:\Users\Administrator\.m2\repository\com\rabbitmq\amqp-client\5.4.3\amqp-client-5.4.3.jar;C:\Users\Administrator\.m2\repository\org\slf4j\slf4j-api\1.7.25\slf4j-api-1.7.25.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-messaging\5.1.9.RELEASE\spring-messaging-5.1.9.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-tx\5.1.9.RELEASE\spring-tx-5.1.9.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-test\5.3.10\spring-test-5.3.10.jar;C:\Users\Administrator\.m2\repository\junit\junit\4.13.2\junit-4.13.2.jar;C:\Users\Administrator\.m2\repository\org\hamcrest\hamcrest-core\1.3\hamcrest-core-1.3.jar" com.intellij.rt.junit.JUnitStarter -ideVersion5 -junit4 cn.dzz.SpringProducerTest,sendingReliableTest
SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
确认消息真的从生产者服务发送到了RabbitMQ中间件这里, 然后这个周期的时刻需要做的什么事情 。。。。
rabbitMQ收到消息了 null Process finished with exit code 0
如果更改错误的配置:
把交换机故意写错,
rabbitTemplate.convertAndSend("confirm-test-exchange222", "confirm", " 发送一条消息以测试confirm回调。。。。");
然后则输出:
"C:\Program Files (x86)\Java\jdk1.8.0_291\bin\java.exe" -ea -Didea.test.cyclic.buffer.size=1048576 "-javaagent:C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\lib\idea_rt.jar=51948:C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\bin" -Dfile.encoding=UTF-8 -classpath "C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\lib\idea_rt.jar;C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\plugins\junit\lib\junit5-rt.jar;C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\plugins\junit\lib\junit-rt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\charsets.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\deploy.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\access-bridge-32.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\cldrdata.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\dnsns.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\jaccess.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\jfxrt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\localedata.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\nashorn.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunec.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunjce_provider.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunmscapi.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunpkcs11.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\zipfs.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\javaws.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jce.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jfr.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jfxswt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jsse.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\management-agent.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\plugin.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\resources.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\rt.jar;C:\Users\Administrator\IdeaProjects\RabbitMQ\Spring-RabbitMQ-Producer\target\test-classes;C:\Users\Administrator\IdeaProjects\RabbitMQ\Spring-RabbitMQ-Producer\target\classes;C:\Users\Administrator\.m2\repository\org\springframework\spring-context\5.3.10\spring-context-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-aop\5.3.10\spring-aop-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-beans\5.3.10\spring-beans-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-core\5.3.10\spring-core-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-jcl\5.3.10\spring-jcl-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-expression\5.3.10\spring-expression-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\amqp\spring-rabbit\2.1.8.RELEASE\spring-rabbit-2.1.8.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\amqp\spring-amqp\2.1.8.RELEASE\spring-amqp-2.1.8.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\retry\spring-retry\1.2.4.RELEASE\spring-retry-1.2.4.RELEASE.jar;C:\Users\Administrator\.m2\repository\com\rabbitmq\amqp-client\5.4.3\amqp-client-5.4.3.jar;C:\Users\Administrator\.m2\repository\org\slf4j\slf4j-api\1.7.25\slf4j-api-1.7.25.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-messaging\5.1.9.RELEASE\spring-messaging-5.1.9.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-tx\5.1.9.RELEASE\spring-tx-5.1.9.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-test\5.3.10\spring-test-5.3.10.jar;C:\Users\Administrator\.m2\repository\junit\junit\4.13.2\junit-4.13.2.jar;C:\Users\Administrator\.m2\repository\org\hamcrest\hamcrest-core\1.3\hamcrest-core-1.3.jar" com.intellij.rt.junit.JUnitStarter -ideVersion5 -junit4 cn.dzz.SpringProducerTest,sendingReliableTest
SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
确认消息真的从生产者服务发送到了RabbitMQ中间件这里, 然后这个周期的时刻需要做的什么事情 。。。。
rabbitMQ没收到消息 : cause by channel error; protocol method: #method<channel.close>(reply-code=404, reply-text=NOT_FOUND - no exchange 'confirm-test-exchange222' in vhost '/dzz', class-id=60, method-id=40)
Process finished with exit code 0
2、消息投递回退
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:rabbit="http://www.springframework.org/schema/rabbit"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
https://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/rabbit
http://www.springframework.org/schema/rabbit/spring-rabbit.xsd">
<!--加载配置文件-->
<context:property-placeholder location="classpath:rabbitmq.properties"/> <!-- 定义rabbitmq connectionFactory publisher-confirms="true" 消息发送可确认
publisher-returns="true"
-->
<rabbit:connection-factory id="connectionFactory" host="${rabbitmq.host}"
port="${rabbitmq.port}"
username="${rabbitmq.username}"
password="${rabbitmq.password}"
virtual-host="${rabbitmq.virtual-host}"
publisher-confirms="true"
publisher-returns="true"
/>
<!--定义管理交换机、队列-->
<rabbit:admin connection-factory="connectionFactory"/> <!--定义rabbitTemplate对象操作可以在代码中方便发送消息-->
<rabbit:template id="rabbitTemplate" connection-factory="connectionFactory"/> <!-- 消息可靠性投递 -->
<rabbit:queue id="confirm-test-queue" name="confirm-test-queue" />
<rabbit:direct-exchange name="confirm-test-exchange" >
<rabbit:bindings>
<rabbit:binding queue="confirm-test-queue" key="confirm" />
</rabbit:bindings>
</rabbit:direct-exchange> </beans>
测试类编写:
package cn.dzz; import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.connection.CorrelationData;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; @RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath*:producer-config.xml")
public class SpringProducerTest { @Autowired
private RabbitTemplate rabbitTemplate; /**
* 消息送出可靠性测试
* 1、xml配置数据连接工厂开启消息可确认设置 √
* 2、rabbitTemplate对象定义回调函数
*/
@Test
public void sendingReliableTest() { /**
* CorrelationData correlationData相关配置信息
* boolean ack 来自交换机收到消息的确认参数 true收到了 false没收到
* String cause 失败的原因信息 发送成功了就没有失败原因 case为null
*/
rabbitTemplate.setConfirmCallback((correlationData, ack, cause) -> {
System.out.println("确认消息真的从生产者服务发送到了RabbitMQ中间件这里, 然后这个周期的时刻需要做的什么事情 。。。。");
if (ack) {
System.out.println("rabbitMQ收到消息了 " + cause);
} else {
System.out.println("rabbitMQ没收到消息 : cause by " + cause);
// 如果没收到就需要做对应的处理逻辑
}
});
rabbitTemplate.convertAndSend("confirm-test-exchange", "confirm", " 发送一条消息以测试confirm回调。。。。");
} /**
* 消息发送给Exchange后, Exchange路由分配给Queue的过程发生了失败,触发ReturnCallBack
* 1、开启回退配置项
* 2、重写回退函数
* 3、设置交换机处理消息的模式
*
*/
@Test
public void sendingReliableTest2() { // 设置交换机处理消息的模式 把发送失败的消息返回给生产者服务, 生产者服务把消息丢尽这个return回调里面
rabbitTemplate.setMandatory(true); /**
*
* @param Message message 交换机分配队列失败的送出消息
* @param int i 错误状态码
* @param String s 错误原因
* @param String s1 交换机名称
* @param String s2 路由键
*/
rabbitTemplate.setReturnCallback((message, i, s, s1, s2) -> {
System.out.println("交换机分配到队列过程失败, ReturnCallback触发....");
System.out.println(
"backed message -> " + message
+ "\nstatusCode -> " + i
+ "\nreason -> " + s
+ "\nexchangeName -> " + s1
+ "\nroutineKey -> " + s2
);
}); // 这里故意设置错误的路由键,让交换机无法分配到,从而触发上面这个函数
rabbitTemplate.convertAndSend("confirm-test-exchange", "confirm222", " 发送一条消息以测试confirm回调。。。。");
} }
结果打印:
"C:\Program Files (x86)\Java\jdk1.8.0_291\bin\java.exe" -ea -Didea.test.cyclic.buffer.size=1048576 "-javaagent:C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\lib\idea_rt.jar=55082:C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\bin" -Dfile.encoding=UTF-8 -classpath "C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\lib\idea_rt.jar;C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\plugins\junit\lib\junit5-rt.jar;C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\plugins\junit\lib\junit-rt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\charsets.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\deploy.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\access-bridge-32.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\cldrdata.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\dnsns.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\jaccess.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\jfxrt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\localedata.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\nashorn.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunec.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunjce_provider.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunmscapi.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunpkcs11.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\zipfs.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\javaws.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jce.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jfr.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jfxswt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jsse.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\management-agent.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\plugin.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\resources.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\rt.jar;C:\Users\Administrator\IdeaProjects\RabbitMQ\Spring-RabbitMQ-Producer\target\test-classes;C:\Users\Administrator\IdeaProjects\RabbitMQ\Spring-RabbitMQ-Producer\target\classes;C:\Users\Administrator\.m2\repository\org\springframework\spring-context\5.3.10\spring-context-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-aop\5.3.10\spring-aop-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-beans\5.3.10\spring-beans-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-core\5.3.10\spring-core-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-jcl\5.3.10\spring-jcl-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-expression\5.3.10\spring-expression-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\amqp\spring-rabbit\2.1.8.RELEASE\spring-rabbit-2.1.8.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\amqp\spring-amqp\2.1.8.RELEASE\spring-amqp-2.1.8.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\retry\spring-retry\1.2.4.RELEASE\spring-retry-1.2.4.RELEASE.jar;C:\Users\Administrator\.m2\repository\com\rabbitmq\amqp-client\5.4.3\amqp-client-5.4.3.jar;C:\Users\Administrator\.m2\repository\org\slf4j\slf4j-api\1.7.25\slf4j-api-1.7.25.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-messaging\5.1.9.RELEASE\spring-messaging-5.1.9.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-tx\5.1.9.RELEASE\spring-tx-5.1.9.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-test\5.3.10\spring-test-5.3.10.jar;C:\Users\Administrator\.m2\repository\junit\junit\4.13.2\junit-4.13.2.jar;C:\Users\Administrator\.m2\repository\org\hamcrest\hamcrest-core\1.3\hamcrest-core-1.3.jar" com.intellij.rt.junit.JUnitStarter -ideVersion5 -junit4 cn.dzz.SpringProducerTest,sendingReliableTest2
SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
交换机分配到队列过程失败, ReturnCallback触发....
backed message -> (Body:' 发送一条消息以测试confirm回调。。。。' MessageProperties [headers={}, contentType=text/plain, contentEncoding=UTF-8, contentLength=0, receivedDeliveryMode=PERSISTENT, priority=0, deliveryTag=0])
statusCode -> 312
reason -> NO_ROUTE
exchangeName -> confirm-test-exchange
routineKey -> confirm222 Process finished with exit code 0
3、消费确认
Ack 确认的意思,即消费者服务收到了来自RabbitMQ队列发送的消息之后,需要做出回应
这个过程就是确认
确认的三种方式
1、自动确认,RabbitMQ发送给消费者服务之后默认认为确认已收到
2、手动确认,等待消费者做出回应之后确认
3、根据异常来进行确认
演示案例:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:rabbit="http://www.springframework.org/schema/rabbit"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
https://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/rabbit
http://www.springframework.org/schema/rabbit/spring-rabbit.xsd">
<!--加载配置文件-->
<context:property-placeholder location="classpath:rabbitmq.properties"/> <!-- 定义rabbitmq connectionFactory -->
<rabbit:connection-factory id="connectionFactory" host="${rabbitmq.host}"
port="${rabbitmq.port}"
username="${rabbitmq.username}"
password="${rabbitmq.password}"
virtual-host="${rabbitmq.virtual-host}"/> <context:component-scan base-package="cn.dzz.rabbitmq.listener" /> <!--定义监听器容器-->
<rabbit:listener-container connection-factory="connectionFactory" auto-declare="true">
<rabbit:listener ref="acknowledgeListener" queue-names="confirm-test-queue" />
</rabbit:listener-container> </beans>
监听器注册:
package cn.dzz.rabbitmq.listener; import org.springframework.amqp.core.Message;
import org.springframework.amqp.core.MessageListener;
import org.springframework.stereotype.Component; import java.nio.charset.StandardCharsets; @Component
public class AcknowledgeListener implements MessageListener {
@Override
public void onMessage(Message message) {
System.out.println(new String(message.getBody(), StandardCharsets.UTF_8));
}
}
测试监听器接收消息是否正常:
"C:\Program Files (x86)\Java\jdk1.8.0_291\bin\java.exe" -ea -Didea.test.cyclic.buffer.size=1048576 "-javaagent:C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\lib\idea_rt.jar=65001:C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\bin" -Dfile.encoding=UTF-8 -classpath "C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\lib\idea_rt.jar;C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\plugins\junit\lib\junit5-rt.jar;C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\plugins\junit\lib\junit-rt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\charsets.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\deploy.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\access-bridge-32.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\cldrdata.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\dnsns.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\jaccess.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\jfxrt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\localedata.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\nashorn.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunec.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunjce_provider.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunmscapi.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunpkcs11.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\zipfs.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\javaws.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jce.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jfr.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jfxswt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jsse.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\management-agent.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\plugin.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\resources.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\rt.jar;C:\Users\Administrator\IdeaProjects\RabbitMQ\Spring-RabbitMQ-Consumer\target\test-classes;C:\Users\Administrator\IdeaProjects\RabbitMQ\Spring-RabbitMQ-Consumer\target\classes;C:\Users\Administrator\.m2\repository\org\springframework\spring-context\5.3.10\spring-context-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-aop\5.3.10\spring-aop-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-beans\5.3.10\spring-beans-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-core\5.3.10\spring-core-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-jcl\5.3.10\spring-jcl-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-expression\5.3.10\spring-expression-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\amqp\spring-rabbit\2.1.8.RELEASE\spring-rabbit-2.1.8.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\amqp\spring-amqp\2.1.8.RELEASE\spring-amqp-2.1.8.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\retry\spring-retry\1.2.4.RELEASE\spring-retry-1.2.4.RELEASE.jar;C:\Users\Administrator\.m2\repository\com\rabbitmq\amqp-client\5.4.3\amqp-client-5.4.3.jar;C:\Users\Administrator\.m2\repository\org\slf4j\slf4j-api\1.7.25\slf4j-api-1.7.25.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-messaging\5.1.9.RELEASE\spring-messaging-5.1.9.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-tx\5.1.9.RELEASE\spring-tx-5.1.9.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-test\5.3.10\spring-test-5.3.10.jar;C:\Users\Administrator\.m2\repository\junit\junit\4.13.2\junit-4.13.2.jar;C:\Users\Administrator\.m2\repository\org\hamcrest\hamcrest-core\1.3\hamcrest-core-1.3.jar" com.intellij.rt.junit.JUnitStarter -ideVersion5 -junit4 SpringConsumerTest,simpleListenerTest
SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
发送一条消息以测试confirm回调。。。。
监听测试 Process finished with exit code 0
RabbitMQ默认状态是使用none表示确认状态
手动签收确认的配置:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:rabbit="http://www.springframework.org/schema/rabbit"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
https://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/rabbit
http://www.springframework.org/schema/rabbit/spring-rabbit.xsd">
<!--加载配置文件-->
<context:property-placeholder location="classpath:rabbitmq.properties"/> <!-- 定义rabbitmq connectionFactory -->
<rabbit:connection-factory id="connectionFactory" host="${rabbitmq.host}"
port="${rabbitmq.port}"
username="${rabbitmq.username}"
password="${rabbitmq.password}"
virtual-host="${rabbitmq.virtual-host}"/> <context:component-scan base-package="cn.dzz.rabbitmq.listener" /> <!--
定义监听器容器 acknowledge="manual" 默认就是none
-->
<rabbit:listener-container connection-factory="connectionFactory" auto-declare="true" acknowledge="manual">
<rabbit:listener ref="acknowledgeListener" queue-names="confirm-test-queue" />
</rabbit:listener-container> </beans>
监听器实现调整:
package cn.dzz.rabbitmq.listener; import com.rabbitmq.client.Channel;
import org.springframework.amqp.core.Message;
import org.springframework.amqp.core.MessageListener;
import org.springframework.amqp.rabbit.listener.api.ChannelAwareMessageListener;
import org.springframework.stereotype.Component; import java.io.IOException;
import java.nio.charset.StandardCharsets; /**
* 手动确认配置:
* 1、监听器容器配置项acknowledge更改为manual
* <rabbit:listener-container connection-factory="connectionFactory" auto-declare="true" acknowledge="manual">
* <rabbit:listener ref="acknowledgeListener" queue-names="confirm-test-queue" />
* </rabbit:listener-container>
*
* 2、监听器改用实现ChannelAwareMessageListener接口
*
* 3、消息处理成功 调用basicAck()签收响应
* 4、处理失败 调用basicNack()签收拒绝 broker重新发送
*
*
*/
@Component
public class AcknowledgeListener implements ChannelAwareMessageListener {
@Override
public void onMessage(Message message, Channel channel) throws Exception {
long deliveryTag = 0;
Thread.sleep(2000); // 让消息别那么快的一直发送,慢点发 try { System.out.println(new String(message.getBody(), StandardCharsets.UTF_8)); // 处理业务逻辑
// todo... int i = 10 / 0; // 这个异常会被捕获,然后触发RabbitMQ一直让消息重新入列发送 // 业务签收
deliveryTag = message.getMessageProperties().getDeliveryTag(); channel.basicAck(deliveryTag, true); } catch (Exception exception) {
exception.printStackTrace(); /**
* public void basicNack(long deliveryTag, boolean multiple, boolean requeue) throws IOException {
* long realTag = deliveryTag - this.activeDeliveryTagOffset;
* if (multiple && deliveryTag == 0L) {
* realTag = 0L;
* } else if (realTag <= 0L) {
* return;
* }
*
* this.transmit(new Nack(realTag, multiple, requeue));
* this.metricsCollector.basicNack(this, deliveryTag);
* }
* long deliveryTag 签收的标签
* boolean multiple 允许签收多条消息?
* boolean requeue 是否重回队列? 消息重新入列?RabbitMQ重新发送
*/
channel.basicNack(deliveryTag, true, true); /**
* 和上面区别就是没有多消息签收的参数
* public void basicReject(long deliveryTag, boolean requeue) throws IOException {
* long realTag = deliveryTag - this.activeDeliveryTagOffset;
* if (realTag > 0L) {
* this.transmit(new Reject(realTag, requeue));
* this.metricsCollector.basicReject(this, deliveryTag);
* }
*
* }
* channel.basicReject(deliveryTag, true);
*/ }
}
}
报错之后 执行拒绝签收,RabbitMQ会一直重新发送消息
消息状态处于一直未签收的状态:
异常处理的两个方法区别:就是Nack可以处理多条消息,Reject只能一条
"C:\Program Files (x86)\Java\jdk1.8.0_291\bin\java.exe" -ea -Didea.test.cyclic.buffer.size=1048576 "-javaagent:C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\lib\idea_rt.jar=50417:C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\bin" -Dfile.encoding=UTF-8 -classpath "C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\lib\idea_rt.jar;C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\plugins\junit\lib\junit5-rt.jar;C:\Program Files\JetBrains\IntelliJ IDEA 2021.2.1\plugins\junit\lib\junit-rt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\charsets.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\deploy.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\access-bridge-32.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\cldrdata.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\dnsns.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\jaccess.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\jfxrt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\localedata.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\nashorn.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunec.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunjce_provider.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunmscapi.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\sunpkcs11.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\ext\zipfs.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\javaws.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jce.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jfr.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jfxswt.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\jsse.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\management-agent.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\plugin.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\resources.jar;C:\Program Files (x86)\Java\jdk1.8.0_291\jre\lib\rt.jar;C:\Users\Administrator\IdeaProjects\RabbitMQ\Spring-RabbitMQ-Consumer\target\test-classes;C:\Users\Administrator\IdeaProjects\RabbitMQ\Spring-RabbitMQ-Consumer\target\classes;C:\Users\Administrator\.m2\repository\org\springframework\spring-context\5.3.10\spring-context-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-aop\5.3.10\spring-aop-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-beans\5.3.10\spring-beans-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-core\5.3.10\spring-core-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-jcl\5.3.10\spring-jcl-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-expression\5.3.10\spring-expression-5.3.10.jar;C:\Users\Administrator\.m2\repository\org\springframework\amqp\spring-rabbit\2.1.8.RELEASE\spring-rabbit-2.1.8.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\amqp\spring-amqp\2.1.8.RELEASE\spring-amqp-2.1.8.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\retry\spring-retry\1.2.4.RELEASE\spring-retry-1.2.4.RELEASE.jar;C:\Users\Administrator\.m2\repository\com\rabbitmq\amqp-client\5.4.3\amqp-client-5.4.3.jar;C:\Users\Administrator\.m2\repository\org\slf4j\slf4j-api\1.7.25\slf4j-api-1.7.25.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-messaging\5.1.9.RELEASE\spring-messaging-5.1.9.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-tx\5.1.9.RELEASE\spring-tx-5.1.9.RELEASE.jar;C:\Users\Administrator\.m2\repository\org\springframework\spring-test\5.3.10\spring-test-5.3.10.jar;C:\Users\Administrator\.m2\repository\junit\junit\4.13.2\junit-4.13.2.jar;C:\Users\Administrator\.m2\repository\org\hamcrest\hamcrest-core\1.3\hamcrest-core-1.3.jar" com.intellij.rt.junit.JUnitStarter -ideVersion5 -junit4 SpringConsumerTest,simpleListenerTest
SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
监听测试
发送一条消息以测试confirm回调。。。。
java.lang.ArithmeticException: / by zero
at cn.dzz.rabbitmq.listener.AcknowledgeListener.onMessage(AcknowledgeListener.java:40)
at org.springframework.amqp.rabbit.listener.adapter.MessageListenerAdapter.onMessage(MessageListenerAdapter.java:272)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doInvokeListener(AbstractMessageListenerContainer.java:1542)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.actualInvokeListener(AbstractMessageListenerContainer.java:1468)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.invokeListener(AbstractMessageListenerContainer.java:1456)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doExecuteListener(AbstractMessageListenerContainer.java:1451)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.executeListener(AbstractMessageListenerContainer.java:1400)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.doReceiveAndExecute(SimpleMessageListenerContainer.java:870)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.receiveAndExecute(SimpleMessageListenerContainer.java:854)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.access$1600(SimpleMessageListenerContainer.java:78)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.mainLoop(SimpleMessageListenerContainer.java:1137)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.run(SimpleMessageListenerContainer.java:1043)
at java.lang.Thread.run(Thread.java:748)
发送一条消息以测试confirm回调。。。。
java.lang.ArithmeticException: / by zero
at cn.dzz.rabbitmq.listener.AcknowledgeListener.onMessage(AcknowledgeListener.java:40)
at org.springframework.amqp.rabbit.listener.adapter.MessageListenerAdapter.onMessage(MessageListenerAdapter.java:272)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doInvokeListener(AbstractMessageListenerContainer.java:1542)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.actualInvokeListener(AbstractMessageListenerContainer.java:1468)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.invokeListener(AbstractMessageListenerContainer.java:1456)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doExecuteListener(AbstractMessageListenerContainer.java:1451)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.executeListener(AbstractMessageListenerContainer.java:1400)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.doReceiveAndExecute(SimpleMessageListenerContainer.java:870)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.receiveAndExecute(SimpleMessageListenerContainer.java:854)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.access$1600(SimpleMessageListenerContainer.java:78)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.mainLoop(SimpleMessageListenerContainer.java:1137)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.run(SimpleMessageListenerContainer.java:1043)
at java.lang.Thread.run(Thread.java:748)
发送一条消息以测试confirm回调。。。。
java.lang.ArithmeticException: / by zero
at cn.dzz.rabbitmq.listener.AcknowledgeListener.onMessage(AcknowledgeListener.java:40)
at org.springframework.amqp.rabbit.listener.adapter.MessageListenerAdapter.onMessage(MessageListenerAdapter.java:272)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doInvokeListener(AbstractMessageListenerContainer.java:1542)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.actualInvokeListener(AbstractMessageListenerContainer.java:1468)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.invokeListener(AbstractMessageListenerContainer.java:1456)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doExecuteListener(AbstractMessageListenerContainer.java:1451)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.executeListener(AbstractMessageListenerContainer.java:1400)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.doReceiveAndExecute(SimpleMessageListenerContainer.java:870)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.receiveAndExecute(SimpleMessageListenerContainer.java:854)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.access$1600(SimpleMessageListenerContainer.java:78)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.mainLoop(SimpleMessageListenerContainer.java:1137)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.run(SimpleMessageListenerContainer.java:1043)
at java.lang.Thread.run(Thread.java:748)
发送一条消息以测试confirm回调。。。。
java.lang.ArithmeticException: / by zero
at cn.dzz.rabbitmq.listener.AcknowledgeListener.onMessage(AcknowledgeListener.java:40)
at org.springframework.amqp.rabbit.listener.adapter.MessageListenerAdapter.onMessage(MessageListenerAdapter.java:272)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doInvokeListener(AbstractMessageListenerContainer.java:1542)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.actualInvokeListener(AbstractMessageListenerContainer.java:1468)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.invokeListener(AbstractMessageListenerContainer.java:1456)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doExecuteListener(AbstractMessageListenerContainer.java:1451)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.executeListener(AbstractMessageListenerContainer.java:1400)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.doReceiveAndExecute(SimpleMessageListenerContainer.java:870)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.receiveAndExecute(SimpleMessageListenerContainer.java:854)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.access$1600(SimpleMessageListenerContainer.java:78)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.mainLoop(SimpleMessageListenerContainer.java:1137)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.run(SimpleMessageListenerContainer.java:1043)
at java.lang.Thread.run(Thread.java:748)
发送一条消息以测试confirm回调。。。。
java.lang.ArithmeticException: / by zero
at cn.dzz.rabbitmq.listener.AcknowledgeListener.onMessage(AcknowledgeListener.java:40)
at org.springframework.amqp.rabbit.listener.adapter.MessageListenerAdapter.onMessage(MessageListenerAdapter.java:272)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doInvokeListener(AbstractMessageListenerContainer.java:1542)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.actualInvokeListener(AbstractMessageListenerContainer.java:1468)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.invokeListener(AbstractMessageListenerContainer.java:1456)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doExecuteListener(AbstractMessageListenerContainer.java:1451)
at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.executeListener(AbstractMessageListenerContainer.java:1400)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.doReceiveAndExecute(SimpleMessageListenerContainer.java:870)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.receiveAndExecute(SimpleMessageListenerContainer.java:854)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.access$1600(SimpleMessageListenerContainer.java:78)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.mainLoop(SimpleMessageListenerContainer.java:1137)
at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.run(SimpleMessageListenerContainer.java:1043)
at java.lang.Thread.run(Thread.java:748)
发送一条消息以测试confirm回调。。。。
【RabbitMQ】08 深入部分P1 可靠性投递的更多相关文章
- RabbitMQ可靠性投递及高可用集群
可靠性投递: 首先需要明确,效率与可靠性是无法兼得的,如果要保证每一个环节都成功,势必会对消息的收发效率造成影响.如果是一些业务实时一致性要求不是特别高的场合,可以牺牲一些可靠性来换取效率. 要保证消 ...
- SpringBoot整合RabbitMQ-消息可靠性投递
本系列是学习SpringBoot整合RabbitMQ的练手,包含服务安装,RabbitMQ整合SpringBoot2.x,消息可靠性投递实现等三篇博客. 学习路径:https://www.imooc. ...
- rabbitMq可靠性投递之手动ACK
#手动应答#spring.rabbitmq.listener.simple.acknowledge-mode=manual#spring.rabbitmq.listener.simple.acknow ...
- rabbitMq可靠性投递之配置(消息至交换机,至队列不通的回调)
@Bean public RabbitTemplate rabbitTemplate(CachingConnectionFactory factory) { //若使用confirm-callback ...
- 四种途径提高RabbitMQ传输消息数据的可靠性(一)
前言 RabbitMQ虽然有对队列及消息等的一些持久化设置,但其实光光只是这一个是不能够保障数据的可靠性的,下面我们提出这样的质疑: (1)RabbitMQ生产者是不知道自己发布的消息是否已经正确达到 ...
- 【RabbitMQ】如何进行消息可靠投递【上篇】
说明 前几天,突然发生线上报警,钉钉连发了好几条消息,一看是RabbitMQ相关的消息,心头一紧,难道翻车了? [橙色报警] 应用[xxx]在[08-15 16:36:04]发生[错误日志异常],al ...
- RabbitMQ 和 Kafka 的消息可靠性对比
RabbitMQ和Kafka都提供持久的消息保证.两者都提供至少一次和至多一次的保证,另外,Kafka在某些限定情况下可以提供精确的一次(exactly-once)保证. 让我们首先理解一下上述术语的 ...
- RabbitMQ学习之集群消息可靠性测试
之前介绍过关于消息发送和接收的可靠性:RabbitMQ学习之消息可靠性及特性 下面主要介绍一下集群环境下,rabbitmq实例宕机的情况下,消息的可靠性.验证rabbitmq版本[3.4.1]. 集群 ...
- 【RabbitMQ】如何进行消息可靠投递【下篇】
说明 上一篇文章里,我们了解了如何保证消息被可靠投递到RabbitMQ的交换机中,但还有一些不完美的地方,试想一下,如果向RabbitMQ服务器发送一条消息,服务器确实也接收到了这条消息,于是给你返回 ...
- 四种途径提高RabbitMQ传输数据的可靠性(二)
前言 上一篇四种途径提高RabbitMQ传输消息数据的可靠性(一)已经介绍了两种方式提高数据可靠性传输的方法,本篇针对上一篇中提出的问题(1)与问题(2)提出解决常用的方法. 本文其实也就是结合以上四 ...
随机推荐
- 使用python批量获取excel的sheet名称
这个脚本的重用是批量读取excel并获取每个excel的所有sheet名输出到一个文件中. 环境:python 3.7.3 1 # -*- coding:utf-8 -*- 2 3 ''' 4 本代码 ...
- .NET C# 程序自动更新组件
引言 本来博主想偷懒使用AutoUpdater.NET组件,但由于博主项目有些特殊性和它的功能过于多,于是博主自己实现一个轻量级独立自动更新组件,可稍作修改集成到大家自己项目中,比如:WPF/Winf ...
- 数据库系列16:MyISAM与InnoDB的索引对比
相关文章 数据库系列:MySQL慢查询分析和性能优化 数据库系列:MySQL索引优化总结(综合版) 数据库系列:高并发下的数据字段变更 数据库系列:覆盖索引和规避回表 数据库系列:数据库高可用及无损扩 ...
- kettle从入门到精通 第五十二课 ETL之kettle Avro output
1.上一节课我们学习了avro input,本节课我们一起学习下avro out步骤. 本节课通过json input 加载json文件,通过avro out 生成avro二进制文件,写日志步骤打印日 ...
- 高可用集群MHA方案
爱奇艺在用的数据库高可用方案 MHA 是目前比较成熟及流行的 MySQL 高可用解决方案,很多互联网公司正是直接使用或者基于 MHA 的架构进行改造实现 MySQL 的高可用. MHA 能在 30 秒 ...
- CPU的一、二、三级缓存的区别
引言 概念 缓存大小也是CPU的重要指标之一,而且缓存的结构和大小对CPU速度的影响非常大,CPU内缓存的运行频率极高,一般是和处理器同频 运作,工作效率远远大于系统内存和硬盘.实际工作时,CPU往往 ...
- springboot项目配置多数据源
springboot项目配置多数据源 //关键:mybatis文件的目录需要区分开来 sqlSessionFactoryBean.setMapperLocations(new PathMatching ...
- python pymysql 数据库查询操作
import pymysql db= pymysql.connect(host="", user='', database="", password='') c ...
- Mirror多人联网发布阿里云
Mirror多人联网发布阿里云 新建模板小书匠 将mirror网络地址和端口选为你阿里云服务器上开放的公网地址和端口 IP与端口 2. 在阿里云服务器安全组中开放你所制定的端口 开放阿里云端口 3. ...
- Elasticsearch如何聚合查询多个统计值,如何嵌套聚合?并相互引用,统计索引中某一个字段的空值率?语法是怎么样的?
目录 Elasticsearch聚合查询说明 空值率查询DSL Elasticsearch聚合基础知识扩展 Elasticsearch聚合概念 Script 用法 Elasticsearch聚合查询语 ...