最佳实践

基于多次实践的总结

项目部署结构

为了方便添加维护,推荐用以下组织结构部署

  • 将rocketmq与mongo等安装源码放于 /usr/local/xxx文件夹下,如以下样例

$ cd /usr/local/
$ ls 
....
maven  mongodb  mysql5.7  redis  rocketmq  rocketmq-externals 
  • 通过启动参数配置日志到 /opt/logs/ 文件夹下

#rocketmq 启动 rocketmq位置usr/local/rocketmq/rocketmq-4.5.2下
nohup sh ./bin/mqnamesrv >  /opt/rocketmq-4.5.2/logs/namesrvrun.log 2>&1 &
# 设置broker的部署方式,和日志位置
nohup sh ./bin/mqbroker -c ./conf/2m-2s-async/broker-a.properties -n "xxxx:9876" > /opt/rocketmq-4.5.2/logs/broker-a.log 2>&1 &
  • 设置一个公用的connector-plugins目录,用于所有的connector包存放,如/usr/local/rocketmq-external/connector-plugins

Borker

Broker 角色

​ Broker 角色分为 ASYNC_MASTER(异步主机)、SYNC_MASTER(同步主机)以及SLAVE(从机)。如果对消息的可靠性要求比较严格,可以采用 SYNC_MASTER加SLAVE的部署方式。如果对消息可靠性要求不高,可以采用ASYNC_MASTER加SLAVE的部署方式。如果只是测试方便,则可以选择仅ASYNC_MASTER或仅SYNC_MASTER的部署方式。

3.2 FlushDiskType

​ SYNC_FLUSH(同步刷新)相比于ASYNC_FLUSH(异步处理)会损失很多性能,但是也更可靠,所以需要根据实际的业务场景做好权衡。

3.3 Broker 配置

NameServer

​RocketMQ 中,Name Servers 被设计用来做简单的路由管理。其职责包括:

  • Brokers 定期向每个名称服务器注册路由数据。

  • 名称服务器为客户端,包括生产者,消费者和命令行客户端提供最新的路由信息。​

消息幂等性

RocketMQ无法避免消息重复(Exactly-Once),所以如果业务对消费重复非常敏感,务必要在业务层面进行去重处理。可以借助关系数据库进行去重。首先需要确定消息的唯一键,可以是msgId,也可以是消息内容中的唯一标识字段,例如订单Id等。在消费之前判断唯一键是否在关系数据库中存在。如果不存在则插入,并消费,否则跳过。(实际过程要考虑原子性问题,判断是否存在可以尝试插入,如果报主键冲突,则插入失败,直接跳过)

msgId一定是全局唯一标识符,但是实际使用中,可能会存在相同的消息有两个不同msgId的情况(消费者主动重发、因客户端重投机制导致的重复等),这种情况就需要使业务字段进行重复消费。

参考连接

Last updated