昨天晚上7点左右,对一张表进行加字段,大概200多万条记录,字段90多个的大表,结果造成mysql锁表,进而导致服务不可用。执行语句如下:

  1. ALTER TABLE `sc_stockout_order` ADD `route_remarks` VARCHAR(1024)  CHARACTER SET utf8mb4  NULL  DEFAULT

mysql配置如下:

打开服务期日志,发现有如下报错:

  1. Cause: org.springframework.jdbc.CannotGetJdbcConnectionException: Could not get JDBC Connection;
  2. nested exception is org.apache.tomcat.jdbc.pool.PoolExhaustedException:
  3. [DubboServerHandler-10.162.99.129:20880-thread-105] Timeout: Pool empty.
  4. Unable to fetch a connection in 50 seconds, none available[size:80; busy:79; idle:0; lastwait:50000].
  5. at org.apache.ibatis.exceptions.ExceptionFactory.wrapException(ExceptionFactory.java:26) ~[mybatis-3.2.8.

我们发现数据库jdbc拿不到链接,虽然没有到300最大数据库连接数,但是两台服务器80*2=160个链接数已经达到配置的客户端最大连接数。这边也说明我们客户端配置的链接数不太合理,可以再稍微调大一点。

发现这个问题后,为了尽快恢复线上服务,用show processlist发现ALTER TABLE这条语句导致大量查询语句处于等待状态,赶紧kill 掉修改表格语句的进程,此时系统恢复正常。在这个当中,发现了一条语句如下:

  1. Waiting for table metadata lock

从图中也可以看到活跃连接数到160之后就不变了,kill掉进程后恢复。

事后查找资料:

Mysql在5.6版本之前,直接修改表结构的过程中会锁表,具体的操作步骤如下:
(1)首先创建新的临时表,表结构通过命令ALTAR TABLE新定义的结构
(2)然后把原表中数据导入到临时表
(3)删除原表
(4)最后把临时表重命名为原来的表名

具体ddl如何工作

参考:http://www.cnblogs.com/cchust/p/4639397.html

Mysql 5.6 虽然引入了Online DDL,但是并不是修改表结构的时候,一定不会导致锁表,在一些场景下还是会锁表的,比如
①某个慢SQL或者比较大的结果集的SQL在运行,执行ALTER TABLE时将会导致锁表发生;
②存在一个事务在操作表的时候,执行ALTER TABLE也会导致修改等待;
查看我们mysql的版本:SELECT VERSION();  给出:5.6.16-log
我们通过Mysql的慢SQL控制台,也在发生问题的时间段内没有出现慢SQL,所以需要排除第一种可能性;
由于当时没有保留现场,所以当时是不是由于事物导致的锁表,现在也无从查起,这只能下次查看分析了。

根据这次教训,得到注意项:

1、尽量选择流量小的事后执行。当天20:00要大促,所以19:00大量供应商在操作。当我们选择在22:00左右再次执行时,就没再出现这个问题

2、执行时先看一下有没有未提交的事务,注意查看事物information_schema.innodb_trx表

3、随时关注服务器日志状况,已有问题要先行解决。

4、后续可现在预发环境或测试环境先行模拟,评估风险

Mysql新增字段到大数据表导致锁表的更多相关文章

  1. MySQL数据库如何解决大数据量存储问题

    利用MySQL数据库如何解决大数据量存储问题? 各位高手您们好,我最近接手公司里一个比较棘手的问题,关于如何利用MySQL存储大数据量的问题,主要是数据库中的两张历史数据表,一张模拟量历史数据和一张开 ...

  2. 利用MySQL数据库如何解决大数据量存储问题?

    提问:如何设计或优化千万级别的大表?此外无其他信息,个人觉得这个话题有点范,就只好简单说下该如何做,对于一个存储设计,必须考虑业务特点,收集的信息如下:1.数据的容量:1-3年内会大概多少条数据,每条 ...

  3. mysql第四篇:数据操作之多表查询

    mysql第四篇:数据操作之多表查询 一.多表联合查询 #创建部门 CREATE TABLE IF NOT EXISTS dept ( did int not null auto_increment ...

  4. mysql 导出数据导致锁表

    故事原由:今天同事小星做系统优化时问我一个sql问题,为什么查询慢,我看了一眼,发现用到了表A中的datetime类型列进行时间比较,建议他给datetime类型列加上索引. 可这是生产库,表A里面有 ...

  5. mysql数据库优化方法大数据量查询轻松解决

    1.对查询进行优化,应尽量避免全表扫描,首先应考虑在 where 及 order by 涉及的列上建立索引. 2.应尽量避免在 where 子句中对字段进行 null 值判断,否则将导致引擎放弃使用索 ...

  6. 分享MSSQL、MySql、Oracle的大数据批量导入方法及编程手法细节

    1:MSSQL SQL语法篇: BULK INSERT [ database_name . [ schema_name ] . | schema_name . ] [ table_name | vie ...

  7. Mysql InnoDB 数据更新/删除导致锁表

    一. 如下对账表数据结构 create table t_cgw_ckjnl ( CNL_CODE ) default ' ' not null comment '通道编码', CNL_PLT_CD ) ...

  8. Mysql InnoDB 数据更新导致锁表

    一.数据表结构 CREATE TABLE `jx_attach` ( `attach_id` int(11) NOT NULL AUTO_INCREMENT, `feed_id` int(11) DE ...

  9. Hiver 操作 MySQL 导致锁表

    Hadoop 搬迁到新集群后,操作主库 MySQL 导致了锁表...sad 具体锁表时间点  : 2016-1-14 14:31  到   2016-1-14 14:36 之间 在 oradba 的 ...

随机推荐

  1. 微信小程序 IView List与Icon结合使用

    wxml <i-cell-group>     <i-cell title="测试" is-link>           <i-icon slot= ...

  2. octave - 用于数值计算的高级交互式语言

    SYNOPSIS 总览 octave [options] OPTIONS 选项 octave 全部命令行选项可以通过运行命令 octave --help 来查看. DESCRIPTION 描述 Oct ...

  3. 计算机编号、硬盘序列号和Mac地址查询方法

    (1)计算机编号: SN也就是Serial Number的缩写,中文也就是产品序列号,而电脑的后面一般也有一个这样的SN序列号,那么怎么查看电脑的S/N序列号呢? 方法一: 将笔记本电脑翻过来,然后在 ...

  4. 点击Listview列头排序

    Private Sub ListView1_ColumnClick(ByVal ColumnHeader As MSComctlLib.ColumnHeader) ListView1.Sorted = ...

  5. 二分图最大匹配(匈牙利算法)简介& Example hdu 1150 Machine Schedule

    二分图匹配(匈牙利算法) 1.一个二分图中的最大匹配数等于这个图中的最小点覆盖数 König定理是一个二分图中很重要的定理,它的意思是,一个二分图中的最大匹配数等于这个图中的最小点覆盖数.如果你还不知 ...

  6. Android工具集合

    Drozer – Android APP安全评估工具(附测试案例) http://www.freebuf.com/sectool/26503.html

  7. #pragma 的使用(转)

    尽管 C 和 C++ 都已经有标准,但是几乎每个编译器 (广义,包含连接器等) 扩展一些 C/C++ 关键字. 合理地应用这些关键字,有时候能使我们的工作非常方便.下面随便说说 Visual C++ ...

  8. nacos 动态刷新@ConfigurationProperties

    使用@ConfigurationProperties 可以替换@value   @ConfigurationProperties @Value 注解功能 可以批量注入配置文件中的属性 只能一个个指定注 ...

  9. Spring源码--Bean的管理总结(一)

    前奏 最近看了一系列解析spring管理Bean的源码的文章,在这里总结下,方便日后复盘.文章地址https://www.cnblogs.com/CodeBear/p/10336704.html sp ...

  10. git初步研究2

    $git init Git 使用 git init 命令来初始化一个 Git 仓库,Git 的很多命令都需要在 Git 的仓库中运行,所以 git init 是使用 Git 的第一个命令. 在执行完成 ...