“ERROR 1100 (HY000): Table '<table_name>' was not locked with LOCK TABLES”错误,因为触发器

问题描述 投票:0回答:1

我在模式(

my_table
)上有一个表(
db1
),我正试图迁移到同一服务器上的另一个模式(
db2
)。为此,我在
db1
上创建了一个触发器,用于插入、更新和删除到
my_table
,这实际上将操作复制到
db2.my_table
。一切都在开发中运行良好,但我们有一个奇怪的设置,其中这两个模式位于不同的 docker 图像上以用于迁移目的。所以
db1
在一个容器上,
db2
在另一个容器上,两个不同的mysql服务器实例。

这会导致本地复制触发器出现问题,因此我在其中添加了一个

IF
子句,以确保
db2
在触发之前存在于服务器上。例如,这里是
AFTER INSERT
触发器:

create trigger insert_my_table
    after INSERT
    on db1.my_table
    for each row
begin
    IF
        (SELECT EXISTS(SELECT SCHEMA_NAME
                       FROM INFORMATION_SCHEMA.SCHEMATA
                       WHERE SCHEMA_NAME = 'db2')) THEN
        insert into db2.my_table
        select *
        from db1.my_table ff
        where ff.id = NEW.id
        on duplicate key update db2.my_table.id=NEW.id;
    END IF;
end;

现在我可以毫无问题地在本地

my_table
中插入新行。但是如果我在插入之前尝试锁定表格(例如
mysqldump
):

lock tables `my_table` write;


insert into my_table (id, name, description) value (1, 'test', 'test_desc');

然后我得到这个错误

"ERROR 1100 (HY000): Table 'my_table' was not locked with LOCK TABLES" 

什么给?有什么我忘记了吗?

mysql docker triggers innodb
1个回答
0
投票

我认为问题在于,一旦您锁定了会话中的任何表,该会话就只能访问已为其明确锁定的表。由于您在

my_table
中写信给
db2
,因此您也必须将其锁定。

MySQL锁表

重要的是:

需要锁的会话必须获取它需要的所有锁 在单个 LOCK TABLES 语句中。虽然由此获得的锁是 held,会话只能访问锁定的表。例如,在 以下语句序列,尝试发生错误 访问 t2 因为它没有在 LOCK TABLES 语句中锁定:

mysql> LOCK TABLES t1 READ;
mysql> SELECT COUNT(*) FROM t1;
+----------+
| COUNT(*) |
+----------+
|        3 |
+----------+
mysql> SELECT COUNT(*) FROM t2;
ERROR 1100 (HY000): Table 't2' was not locked with LOCK TABLES

INFORMATION_SCHEMA 数据库中的表是一个例外。即使会话持有通过 LOCK TABLES 获得的表锁,也可以在不显式锁定的情况下访问它们。

© www.soinside.com 2019 - 2024. All rights reserved.