注册
达梦数据库“锁超时”问题处理
专栏/培训园地/ 文章详情 /

达梦数据库“锁超时”问题处理

bilibili 2024/11/27 949 1 0
摘要

过去,在业务系统设计当中,我们一般认为,不要在生产时间段执行对表的DDL操作,例如加列删列等。

但是最近几年,系统设计是变得越来越粗犷了,生产时间段执行DDL操作的业务系统是越来越多,有些业务系统(甚至是核心系统),都逐渐的放弃了对生产时间执行DDL操作的限制,甚至将加列删列加入了正常的业务流程当中。

作为DBA,我们当然对这种行为深恶痛绝,至少是应该相当警惕。但是毕竟系统都已经这么设计了,我们也没啥办法,只能硬上了。

对于业务上执行对表DDL这个事情,主要面临两个问题,一个是大表的数据量大的情况下,加列删列耗时很高,一个是如果表上业务比较频繁,或者耗时很高,经常面临DDL语句被阻塞的问题;

对于大表耗时问题,目前在达梦数据库上已经提供了快速加列功能,alter table opt,可以对加列/修改列/删除列进行优化,实测效果也很好,TB级表也能瞬间加完。这次我们主要讨论锁的问题。

在业务频繁的生产系统上,加列时经常会出现报错“锁超时”,其原因就是DDL被表上的业务阻塞了。在经过了DDL_WAIT_TIME配置的时间(默认10s)之后,如果此ddl还没获取到锁,就会报错“锁超时”(Lock timeout)。
图片1.png
简单的说,在出现“锁超时”报错时,需要通过v$trxwait视图找到阻塞我们DDL的事务,然后通过kill会话或者等待它执行完等方法,让ddl能获取到所需锁。
但是直接操作的话还会面临一个问题,即出现“锁超时”报错后,库里已经查找不到之前的锁阻塞信息了。因此我们还需要手动执行一次DDL,或者业务再触发一次。
但是默认情况下,ddl只会等待10s就报错,就算手动触发后,去查v$trxwait时也来不及了。因此一般建议手动调大DDL_WAIT_TIME参数值。

SP_SET_PARA_VALUE(1,’DDL_WAIT_TIME’,600);

在找到造成阻塞的事务,完成需要的DDL操作后,一定不要忘记把DDL_WAIT_TIME的参数值改回来。毕竟,加列加不上只是影响后面的事儿,要是DDL卡在库里10分钟了,整个业务系统说不定都要被卡10分钟,那影响太大了。

顺便提一下,以前达梦除了在表上加列删列外,创建索引也会出现“锁超时”报错。但是目前的版本已经支持create index online功能了,通过在线创建索引,可以避免创建索引时的“锁超时”报错。

评论
后发表回复

作者

文章

阅读量

获赞

扫一扫
联系客服