广告
返回顶部
首页 > 资讯 > 数据库 >记一次线上问题 → 对 MySQL 的 ON UPDATE CURRENT_TIMESTAMP 的片面认知
  • 384
分享到

记一次线上问题 → 对 MySQL 的 ON UPDATE CURRENT_TIMESTAMP 的片面认知

摘要

开心一刻   老婆痛经,躺在沙发上,两岁的女儿看着她问道   女儿:妈妈,你怎么了   老婆:妈妈肚子痛   女儿:哦,妈妈你头疼   老婆:不是头疼,妈妈是肚子疼   女儿用她的不锈钢饭碗砸向老婆的额头,说道:妈妈,你哪里疼   老婆:

记一次线上问题 → 对 MySQL 的 ON UPDATE CURRENT_TIMESTAMP 的片面认知

开心一刻

  老婆痛经,躺在沙发上,两岁的女儿看着她问道

  女儿:妈妈,你怎么了

  老婆:妈妈肚子痛

  女儿:哦,妈妈你头疼

  老婆:不是头疼,妈妈是肚子疼

  女儿用她的不锈钢饭碗砸向老婆的额头,说道:妈妈,你哪里疼

  老婆:头疼,头疼

  老婆幽怨的看着我,说道:这姑娘随你还是随我

  我低着头,小声地说道:我都被你欺负成啥样了,你说姑娘随谁?

问题背景

  需求背景

  需求:对商品的上架与下架进行管控,下架的商品不能进行销售

    上架与下架的管控,在我负责的项目(单据系统)中实现;销售的控制则是在另外一个项目(POS系统)中实现

    POS 系统定时的从单据系统中拉取数据,并对商品的销售进行控制

  单据系统设计了两张表:

DROP TABLE IF EXISTS t_ware_on_off_bill;
CREATE TABLE `t_ware_on_off_bill` (
  `id` BIGINT(19) NOT NULL AUTO_INCREMENT COMMENT "自增主键",
  `bill_code` VARCHAR(45) NOT NULL COMMENT "单据编号",
  `bill_type` TINYINT(2) NOT NULL DEFAULT 1 COMMENT "单据类型(1=下架,2=上架)",
  `bill_status` TINYINT(2) NOT NULL COMMENT "单据状态(1=草稿,2=已提交,3=审核中,4=已生效,5=已取消)",
  `is_delete` TINYINT(2) NOT NULL DEFAULT "2" COMMENT "是否删除标识(1-是,2-否)",
    `note` VARCHAR(255) NOT NULL DEFAULT "" COMMENT "备注",
  `create_user` BIGINT(19) NOT NULL COMMENT "创建人id",
  `create_time` DATETIME(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) COMMENT "创建时间",
  `modify_user` BIGINT(19) NOT NULL COMMENT "最终修改人",
  `modify_time` DATETIME(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3) COMMENT "最终修改时间",
  PRIMARY KEY (`id`) USING BTREE
) ENGINE=InnoDB COMMENT="商品上架下架单";

DROP TABLE IF EXISTS t_ware_on_off_bill_detail;
CREATE TABLE `t_ware_on_off_bill_detail` (
  `id` BIGINT(19) NOT NULL AUTO_INCREMENT COMMENT "自增主键",
  `bill_id` BIGINT(19) NOT NULL COMMENT "商品上架下架单的id",
  `ware_code` BIGINT(19) NOT NULL COMMENT "商品编号",
  `note` VARCHAR(255) DEFAULT NULL COMMENT "备注",
  PRIMARY KEY (`id`) USING BTREE
) ENGINE=InnoDB COMMENT="商品上架下架单明细";
View Code

  实际上,表的字段不止这么多,但因为表的字段的多少不影响问题的出现,所以也就简化了表结构

  下游系统根据 modify_time 定时进行数据的增量同步( t_ware_on_off_bill 和 t_ware_on_off_bill_detail 都会进行更新)

  部分数据未同步

  结果出现了部分数据未同步的情况

  先来复现下问题,初始数据如下

  此时的 modify_time 的值是 2021-09-08 21:18:52.602 

  我们来执行下更新操作

  可以看到对 t_ware_on_off_bill 的更新结果是: 受影响的行: 0 , modify_time 并未进行更新,其值仍是 2021-09-08 21:18:52.602 

  但是 t_ware_on_off_bill_detail 是实实在在存在更新的

  这就导致下游系统通过 modify_time 没有增量同步最新的商品明细

  问题来了:明明对 t_ware_on_off_bill 的 N 个字段进行了 SET 操作,为什么没有记录受影响(modify_time 为什么不更新) 

探究真相

  我相信此时很多小伙伴都认为楼主是这个

  菜不可怕,怕的是我们不敢面对它;有问题,我们就去找原因,然后解决它(菜的好理直气壮...)

  追查原因

  其实 Mysql 官方文档中有说明:11.2.6 Automatic Initialization and Updating for TIMESTAMP and DATETIME

 

   两种情况会进行自动更新成系统当前时间

    1、insert 行时,该列没有值

    2、该行的任意列的值改变了

  此时,相信大家都知道原因了吧

  虽然这个 sql 很长,SET 了好几个字段,但是不满足上述两点中的任意一点,那么 modify_time 也就不会更新成系统当前时间了

  解决问题

  原因是找到了,如何解决问题了?

  官方文档里面也说明了,显示的设值,也就是我们显示的指定 modify_time 的值,像这样

  我们来看看实际结果

  当然,解决方案不止这一种,各位可以在评论区畅所欲言

总结

  1、mysql 自动设置成系统当前时间是有条件的,否则是不会更新的哦

    insert 行时,该列没有值

    该行的任意列的值改变了

  2、给大家留个疑问:为什么要有任意列的值改变了,MySQL 才会自动更新 modify_time 成当前系统时间,而不是只要有 SET 就更新 modify_time 成当前系统时间

您可能感兴趣的文档:

--结束END--

本文标题: 记一次线上问题 → 对 MySQL 的 ON UPDATE CURRENT_TIMESTAMP 的片面认知

本文链接: https://www.lsjlt.com/news/8742.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作