关于多个会话引起唯一键冲突

关于多个会话引起唯一键冲突
发生唯一键冲突时会发生TX锁争用,进程a执行insert后,若进程b执行insert会引发唯一键冲突,进程b要以shared 模式获取TX锁,
发生等待,进程b会等到进程a提交或者回滚为止,若进程a上完成提交,则b上出现ora-0001。若进程a完成了回滚,则进程b的insert成功完成。
Session A:
[@more@]
--关于多个会话引起唯一键冲突
发生唯一键冲突时会发生TX锁争用,进程a执行insert后,若进程b执行insert会引发唯一键冲突,进程b要以shared 模式获取TX锁,
发生等待,进程b会等到进程a提交或者回滚为止,若进程a上完成提交,则b上出现ora-0001。若进程a完成了回滚,则进程b的insert成功完成。
Session A:
SQL> create table test(id number,birthdate date);
Table created.
SQL> create unique index test_idx on test(id);
Index created.
SQL> insert into test values(1,sysdate);
1 row created.
Session B:
SQL> insert into test values(1,sysdate);
....
wait
Session C:
SQL> select (sysdate-a.logon_time)*24*60 minutes,
2 a.BLOCKING_SESSION,
3 a.sid,
4 a.serial#,
5 a.event,
6 a.p1,
7 a.p2,
8 a.p3,
9 a.sql_id
10 from v$session a, v$sql b
11 where
12 a.sql_address = b.address
13 and a.sql_hash_value = b.hash_value
14 and a.sql_child_number=b.child_number
15 and a.username like 'SH'
16 order by 1 desc;
MINUTES BLOCKING_SESSION SID SERIAL# EVENT P1 P2 P3
---------- ---------------- ---------- ---------- ------------------------- ---------- ---------- ----------
4.95 143 127 639 enq: TX - row lock conten 1415053316 655374 1232
tion
应用程序里面唯一键引起的TX锁争用可能发生,不过如果使用sequence的话就可以避免。

来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/25586587/viewspace-1053999/,如需转载,请注明出处,否则将追究法律责任。

转载于:http://blog.itpub.net/25586587/viewspace-1053999/

<think>嗯,用户的问题是关于如何在MySQL从库上跳过多GTID值的。我需要先回忆一下MySQL的复制机制,特别是GTID相关的处理。GTID(全局事务标识符)在MySQL复制中用于确保每个事务在主库和从库上都有唯一的标识。当从库遇到错误的事务时,可能需要跳过这些事务才能继续复制。 用户提到的是“跳过多GTID值”,也就是可能需要跳过多个事务,而不仅仅是单个。之前处理类似问题时,常用的方法是在从库上设置`gtid_next`,然后执行空事务来跳过特定的GTID。但如果是多个GTID,可能需要重复这个过程,或者找到更高效的方式。 首先,我需要确认用户的环境是否启用了GTID复制。根据用户提供的引用,例如引用[3]中提到了设置主从连接的权限,引用[2]展示了如何设置复制过滤,引用[4]提到了设置只读模式。不过用户的具体情况是GTID跳过,所以需要参考GTID相关的操作步骤。 在MySQL官方文档中,处理GTID错误通常的步骤是停止从库复制,设置会话级别的`gtid_next`为需要跳过的GTID,然后执行空事务,最后恢复复制。但若需要跳过多条,就需要对每个GTID执行这个操作,或者找到批量处理的方法。 另外,用户提供的引用中并没有直接提到GTID跳过的步骤,所以可能需要结合标准操作步骤和用户提供的配置信息来回答。例如,用户可能在配置主从复制时已经启用了GTID,现在需要处理多个错误的事务。 需要注意的是,跳过事务可能会导致数据不一致,因此必须谨慎操作,并在操作后验证数据完整性。此外,如果存在多个错误的事务,可能需要逐个处理每个GTID,或者找到批量跳过的方法。不过,MySQL官方可能没有直接支持批量跳过的命令,因此可能需要编写脚本或手动执行多次。 可能的步骤包括: 1. 停止从库复制:`STOP SLAVE;` 2. 对于每个需要跳过的GTID,设置`gtid_next`并执行空事务。 3. 重启复制:`START SLAVE;` 例如,如果要跳过GTID为aaaa-bbbb-cccc-dddd:5到aaaa-bbbb-cccc-dddd:10,可能需要逐个执行: ```sql SET GTID_NEXT='aaaa-bbbb-cccc-dddd:5'; BEGIN; COMMIT; SET GTID_NEXT='AUTOMATIC'; ``` 重复这个过程直到所有需要跳过的GTID都被处理。 另一种情况是,如果错误是由于某个范围内的多个GTID引起的,用户可能希望直接设置从库的`gtid_purged`来跳过这些事务。但需要注意,`gtid_purged`的设置需要非常小心,否则可能导致数据丢失或复制中断。 此外,用户可能需要先确认需要跳过的GTID范围,可以通过`SHOW SLAVE STATUS\G`查看当前的错误信息,获取具体的GTID值,然后进行处理。 总结回答步骤: 1. 停止从库复制。 2. 获取需要跳过的GTID列表。 3. 为每个GTID执行空事务。 4. 恢复复制并验证状态。 同时,提醒用户注意数据一致性,并建议在操作前备份数据。</think>### MySQL从库跳过多GTID值的方法 在MySQL主从复制中,若从库因某些事务(如重复主键、数据冲突等)中断,需跳过特定GTID(Global Transaction Identifier)值时,可通过以下步骤实现: #### 1. **停止从库复制** ```sql STOP SLAVE; ``` 确保从库停止接收新事务[^4]。 #### 2. **确认需跳过的GTID范围** 通过`SHOW SLAVE STATUS\G`查看错误信息,获取导致中断的GTID值(例如`aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa:1-5`)。 #### 3. **逐条跳过GTID** 对每个需跳过的GTID执行空事务: ```sql SET GTID_NEXT='aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa:1'; BEGIN; COMMIT; SET GTID_NEXT='AUTOMATIC'; ``` 重复此步骤,直至所有目标GTID被处理[^3]。 #### 4. **调整`gtid_executed`** 若需批量跳过连续GTID,可手动更新从库的`gtid_executed`: ```sql RESET MASTER; SET GLOBAL gtid_purged='aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa:1-5'; ``` 此操作会重置从库的GTID历史,需确保主库数据与跳过的事务无依赖[^2]。 #### 5. **恢复复制** ```sql START SLAVE; ``` 验证复制状态: ```sql SHOW SLAVE STATUS\G; ``` 确保`Slave_IO_Running`和`Slave_SQL_Running`均为`Yes`[^1]。 --- ###
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值