项目原本是用spring boot结合mqrabbit来写的,使用提供的框架很简单。但项目作为jar包被别的项目使用,所以项目中的配置文件会被引用的项目中的配置所覆盖,因此想要提高jar包的高可用性,需要自身配置rabbit,配置rabbit工具类,将消息中间件的IP,账号密码等配置到代码中
踩过的坑: 生产者和消费者没有采用编码的来使字符串和字符数组转换。导致最后消费方获取的字符串无法转换为对象,报错。
rabbit工具类中配置了发送和消费信息的方法,可以直接调用
生产消费者发送和获取的信息不一致。
生产方
生产者发送消息,是以byte数组的形式来发送的,
因此将对象转换字符串,再将字符串转换为byte数组
注意:字符串转换为字节数组一定要提供编码格式
*
* @throws
* @author changqing
* @data 2019/10/11 10:45
* @descript: channel.queueDeclare的值依次是:
* queue: 队列名称
* durable: 是否持久化
* exclusive:是否排外的
* autoDelete:是否自动删除
*arguments:队列中的消息什么时候会自动被删除?
*/
channel.queueDeclare(QUEUE_NAME, true, false, false, null);
String message = healthJson;
channel.basicPublish("", QUEUE_NAME, null, message.getBytes("utf-8"));
byte[] bytes = JSON.toJSONBytes(message);
//System.out.println(" [x] Sent '" + message + "'");
log.info(" 生产者 Sent '" + JSON.toJSONBytes(message) + "'");
channel.close();
connection.close();
byte[] byte = message.getBytes(“utf-8”)
这样在消费方获取到字节数组后,也可以用这个编码格式来转化为String,获取的内容一致
消费方
消费方我是用spring boot集合了rabbit框架
这样写利用框架比较简单,可以一直监听信息,
监听到的信息可以是字符串,字节数组,看具体传的是啥
我监听的是byte[]。
== String s = newString(message,“utf-8”);==
用这种编码格式是为了和生产方保持一直,这样转化后的数据是一致的。
我之前没有用编码来转化,导致获取的数值里面有“,\等,导致转换为对象的时候报错。浪费很长的时间。
@Autowired
private SystemLogMapper systemLogMapper;
@RabbitListener(queues = "log_value")
public void receiveMessage( byte[] message) throws UnsupportedEncodingException {
logger.info("获取的信息" + message);
String s = new String(message,"utf-8");
logger.info(s);
if (StringUtils.isNotBlank(s)){
SystemLogPO systemLogPO = JSON.parseObject(s, SystemLogPO.class);
systemLogMapper.insert(systemLogPO);
}
com.rabbitmq.client.ShutdownSignalException: channel error; protocol method。。。。。。
是因为我之前在消息中间件中已经创建的一个队列。
这次创建的时候,队列的名称一样,但是该队列的属性配置不一样,导致报错。
解决方案:
- 取别的名称
- 配置该名称属性和之前的一致。-----该报错最后边有提示哪些属性不一致,可以更改。
- 删除该队列。-------我之前配置的该名称是永久的,因此在图示化中无法删除。可以在服务器中试下,我没试i,觉得没必要。