问题描述

场景是这样的,我们的支付系统在一笔支付完成后,需要发出通知给到商户。支付完成的消息通过消息队列发送给通知的服务。通知服务的有一部分处理逻辑是这样的:

            notifyPersist.saveNotifyRecord(notifyRecord);notifyRecord = rpNotifyService.getNotifyByMerchantNoAndMerchantOrderNoAndNotifyType(notifyRecord.getMerchantNo(), notifyRecord.getMerchantOrderNo(), notifyRecord.getNotifyType());notifyQueue.addElementToList(notifyRecord);

三行代码。我解释下,通知服务收到消息解析成 notifyRecord 对象,然后存入数据库,然后马上取出添加到任务队列。另外又一个独立的线程去处理这个任务队列。

项目上线后,客户反馈偶尔会出现收不到通知的情况。

问题排查

经过日志跟踪,我发现是在上述代码的第二行,查询记录的时候数据库返回null,也就是没有查询到记录。导致任务队列没有该笔支付的通知任务。

一开始觉得非常不解,因为通过日志我们发现第一行代码是执行成功的,既然插入成功了,没理由查询不到啊??而且我去数据库看确定是有这条记录的。莫非是见鬼了!!

我先说下

慢慢静下心来思考,结合这个现象是偶发性的,我想到有没有可能是因为读写分离延时造成的。我先说下我们的存储架构:

centos 6.5 64位操作系统。mycat1.6版本,mysql 5.6.21

数据库服务器有两台,一台主,一台从,利用mycat配置了主从复制和读写分离。写操作在主机上,读操作在从机上。如下图所示:

有没有可能是主库上插入成功后,从库还没有来得急同步完成,应用就马上查询,所以查不到。为了验证我的想法,我把代码改成下面这样发布到生产先看看效果:

notifyPersist.saveNotifyRecord(notifyRecord);
Thread.sleep(300);
notifyRecord = rpNotifyService.getNotifyByMerchantNoAndMerchantOrderNoAndNotifyType(notifyRecord.getMerchantNo(), notifyRecord.getMerchantOrderNo(), notifyRecord.getNotifyType());
notifyQueue.addElementToList(notifyRecord);

思路也很简单粗暴,就是插入之后不马上读,而是等一会让从库同步完再读。发布后,跑了一个段时间,没有反馈异常。证明我怀疑的没错,问题确实出现在mycat读写分离延时上。

解决方案

当然,上面定位问题的sleep也勉强算是一个解决方案。只不过感觉比较low,原理很好理解。在插入数据和查询数据中间加一个sleep()方法,相当于等一会再读。如果应用对时效要求不高,
此方法也不失唯一种快速有效的方案。

找到了问题的根源我就去mycat的官网和相关论坛寻找解决方案。

功夫不负有心人,后来我查到相关资料,mycat可以通过注解的方式指定某些 sql 语句强制走主库,如下所示:

<select id="listBy" parameterType="java.util.Map" resultMap="BaseResultMap">/**mycat:db_type=master*/select * from rp_notify_record<where><include refid="condition_sql" /></where><![CDATA[ order by create_time desc]]></select>

注意到 /** */里面的注解,通过指定 db_type=master 保证后面的 sql 语句走主库。这样就不存在延时导致查询不到的问题了。

生产上遇到的一例mycat读写分离延时问题相关推荐

  1. Mycat 读写分离、主从切换、分库分表的操作记录

    Mycat 读写分离.主从切换.分库分表的操作记录 系统开发中,数据库是非常重要的一个点.除了程序的本身的优化,如:SQL语句优化.代码优化,数据库的处理本身优化也是非常重要的.主从.热备.分表分库等 ...

  2. Mycat读写分离、主从切换、分库分表的操作记录 https://www.cnblogs.com/kevingrace/p/9365840.html

    [此篇文章写得不错] 系统开发中,数据库是非常重要的一个点.除了程序的本身的优化,如:SQL语句优化.代码优化,数据库的处理本身优化也是非常重要的.主从.热备.分表分库等都是系统发展迟早会遇到的技术问 ...

  3. 基于Docker搭建MySQL(MariaDB)+ mycat读写分离测试环境

    1. 手动创建mariadb镜像     创建一个CentOS容器         [yeqiang@localhost ~]$ docker run -it centos /bin/bash    ...

  4. MySQL数据库mycat读写分离

    mycat读写分离 Mycat的读写分离是建立在Mysq的主从复制的基础上的 修改配置文件 schema.xml <?xml version="1.0"?> <! ...

  5. mysql高级技术之mycat读写分离技术实践

    1,课程回顾 2,本章重点 mysql 主从原理,好处mycat 概念,读写分离好处,读写分离的实现 3,具体内容 3.1 mysql 主从 3.1.1 linux下mysql安装 以mysql5.6 ...

  6. MyCat 读写分离与分库分表

    一.Mycat 简介 Mycat 是一个开源的数据库中间件,可以解决分布式数据库环境下的大多数问题,如读写分离.分库分表等,除此之外,它还具备以下特性: 支持 MySQL.Oracle.DB2.SQL ...

  7. MyCat读写分离-笔记(四)

    概述 Mycat能够实现数据库读写分离,不能实现主从同步,数据库的备份还是基于数据库层面的.Mycat只是数据库的中间件: Mycat读写分离配置 在MySQL中间件出现之前,对于MySQL主从集群, ...

  8. mycat读写分离部署步骤

    1.下载mycat: https://raw.githubusercontent.com/MyCATApache/Mycat-download/master/1.5-RELEASE/Mycat-ser ...

  9. 应用 | 同学,该学MyCat实际应用案例与MyCat读写分离了

    Hi!我是小小,一个双鱼座的佛系程序猿,今日的blog将会写关于MyCat最后一点学习内容,读写分离,与MyCat实际应用案例和一个小小的例子. MyCat 读写分离 MyCat的读写分离是建立在My ...

最新文章

  1. CEJ:西安理工赵亚乾组冠状病毒在水中传播特征、可能遏制策略与研究挑战
  2. 单端信号和差分信号的区别
  3. matlab配对交易回测,精品案例 | 经典投资策略之配对交易策略
  4. std中稳定排序算法_敏哥:深挖亚马逊A9算法中的广告搜索排序
  5. PHP的composer dump-autoload
  6. HBase、Redis、MongoDB、Couchbase、LevelDB主流 NoSQL 数据库的对比
  7. 正则表达式验证六位数以上数字,符号,字母任意两种混合的密码验证策略
  8. sqlserver无法连接到服务器的常见原因和解决办法
  9. msfconsole启动失败并报错`not_after=‘: bignum too big to convert into `long‘的解决方法
  10. java map排序_探索Java常用集合
  11. 水系图一般在哪里找得到_如何对于排水系统的服务范围进行统计分析
  12. arma模型预测 matlab,MATLAB中ARMA模型预测差分问题
  13. 虚拟试衣是什么及优势在哪
  14. JavaScript练习题
  15. java邮件群发代码_基于java的邮件群发软件
  16. “番茄工作法” 工欲善其事必先利其器
  17. Unity CardboardSDK解析
  18. NSX-T 恢复DFW策略
  19. arduino(19 ):使用ESP32连接 PS3 蓝牙手柄,需要在windows 上先连接成功,然后在修改mac地址,才可以连接成功,但是目前正在测试中,需要在windows上配对成功。
  20. 倍福Twincat NC PTP使用介绍

热门文章

  1. 简单两招教会您,电脑怎么录屏
  2. 集成学习之Stacking
  3. 探访“全甲格斗”圈 文职员工穿上盔甲就成场上最凶猛的人
  4. 科普:探地雷达发展历史、天线分类,结构组成和工作原理
  5. Android Studio 模拟器无法启动问题(x86 emulation currently requires hardware acceleration。。。)
  6. 《现代通信原理》远程题库(全)
  7. VUE实现的简单拼图游戏
  8. 二维三维动画版心形线附代码
  9. linux忘记密码了怎么解决
  10. Ubuntu16.04保存/home盘下的数据重装Ubuntu系统