为什么我在 BEFORE UPDATE 触发器中没有获得“NEW.value”值?

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

我编写了一个简单的触发器,在更新表之前,将数据输入到其他表中。一切都会好起来的,但是如果在没有 DECLARE 新变量并且没有通过 SET 将数据输入到该变量中的情况下使用 NEW.id 或 NEW.object_id 的值,那么它们的值是空的。但即使在这里我也失败了,因为在将数据输入变量后,我收到像 NAME_CONST ('new_id_object',5159) 这样的数据。

如果您在触发器中注册调试,那么在调试消息中,所有内容都会按其应有的样子写得很漂亮

<------><------>    22 Query<-->SIGNAL SQLSTATE '45000' SET MESSAGE_TEXT =  NAME_CONST('debug_message',_utf8mb3'Debug: NEW.object_id=14, NEW.id=5024, NEW.date1=2021-02-08, NEW.type=1, NEW.cid=6968' COLLATE 'utf8mb3<------><------>    22 Query<-->commit

这是我的触发器:

BEGIN
  DECLARE new_object_id INT;
  SET new_object_id = NEW.object_id;
  GET DIAGNOSTICS new_object_id = NUMBER;
  -- Now you can use new_object_id directly in your trigger logic
  -- For example, you can use it in the INSERT statement
  IF new_object_id != 999 THEN
    INSERT INTO object_param_value_text (object_id, param_id, `value`) VALUES (new_object_id, 1, '123');
  END IF;
END

phone_client_item_1表结构

1   id  int(11) NULL    NULL    NO  NULL    auto_increment      
2   cid int(11) NULL    NULL    NO  NULL            
3   object_id   int(11) NULL    NULL    NO  NULL            
4   type    tinyint(4)  NULL    NULL    NO  NULL            
5   source_id   int(11) NULL    NULL    NO  NULL            
6   date1   date    NULL    NULL    YES NULL            
7   date2   date    NULL    NULL    YES NULL            
8   client_services varchar(100)    utf8mb4 utf8mb4_unicode_ci  NO  NULL            
9   oper_fromports  text    utf8mb4 utf8mb4_unicode_ci  YES NULL            
10  oper_toports    text    utf8mb4 utf8mb4_unicode_ci  YES NULL            
11  oper_fromprefs  text    utf8mb4 utf8mb4_unicode_ci  YES NULL            
12  oper_toprefs    text    utf8mb4 utf8mb4_unicode_ci  YES NULL            
13  oper_not_fromprefs  text    utf8mb4 utf8mb4_unicode_ci  YES NULL            
14  oper_not_toprefs    text    utf8mb4 utf8mb4_unicode_ci  YES NULL            
15  oper_from_range text    utf8mb4 utf8mb4_unicode_ci  YES NULL            
16  oper_to_range   text    utf8mb4 utf8mb4_unicode_ci  YES NULL            
17  oper_service_id int(11) NULL    NULL    NO  NULL            
18  alias   varchar(100)    utf8mb4 utf8mb4_unicode_ci  NO  NULL            
19  comment text    utf8mb4 utf8mb4_unicode_ci  NO  NULL            
20  oper_not_from_range text    utf8mb4 utf8mb4_unicode_ci  NO  NULL            
21  oper_not_to_range   text    utf8mb4 utf8mb4_unicode_ci  NO  NULL

object_param_value_text表结构

3   value   varchar(250)    utf8mb4 utf8mb4_unicode_ci  NO              
1   object_id   int(11) NULL    NULL    NO  NULL            
2   param_id    int(11) NULL    NULL    NO  NULL



SQL 查询自身的 UPDATE 以及触发器生成的查询

<------><------>    42 Prepare<>UPDATE phone_client_item_1 SET cid=?, type=?, source_id=?, date1=?, date2=?,  comment=?, object_id=?, alias=? WHERE id=?
<------><------>    42 Execute<>UPDATE phone_client_item_1 SET cid=6968, type=1, source_id=7, date1=DATE'2021-01-13', date2=NULL,  comment='[LOCAL] ???? ?????', object_id=14, alias='' WHERE id=4990
<------><------>    42 Query<-->INSERT INTO object_param_value_text (object_id, param_id, `value`) VALUES ( NAME_CONST('new_object_id',14), 1, '123')

在此之前,我为另一个表编写了一个触发器,一切都按预期完美运行。

BEGIN

    -- Get the last inserted ID from the object table
    SELECT `AUTO_INCREMENT` INTO @object_id
    FROM INFORMATION_SCHEMA.TABLES
    WHERE TABLE_SCHEMA = 'bgbilling'
    AND TABLE_NAME = 'object';

    -- Modify the values before insert
    SET NEW.date1 = NOW();
    
    -- Use LPAD within CONCAT to format object_id with leading zeros directly
    IF NEW.type_id = 1 THEN
        INSERT INTO object_param_value_text (object_id, param_id, `value`) 
            VALUES (@object_id, 3, CONCAT('sp_', NEW.cid, '-', LPAD(@object_id, 5, '0')));
        INSERT INTO object_param_value_text (object_id, param_id, `value`) 
            VALUES (@object_id, 2, CAST(SUBSTRING(MD5(RAND()), 1, 12) AS CHAR));
        INSERT INTO object_param_value_list (object_id, param_id, `value`) 
            VALUES (@object_id, 10, 16);
        INSERT INTO object_param_value_list (object_id, param_id, `value`) 
            VALUES (@object_id, 11, 20);
        INSERT INTO object_param_value_list (object_id, param_id, `value`) 
            VALUES (@object_id, 12, 21);
        INSERT INTO object_param_value_flag (object_id, param_id, `value`) 
            VALUES (@object_id, 13, 0);
    END IF;
END


我怎样才能大致让我的触发器工作?从 NEW.object_id 获取数据,该数据应该是整数,并在触发器生成的 SQL 查询中使用它

INSERT INTO object_param_value_text (object_id, param_id, value) VALUES (new_object_id, 1, '123');

如果我使用

DECLARE new_object_id INT;
SET new_object_id = NEW.object_id;

真正的 SQL 查询看起来像

INSERT INTO object_param_value_text (object_id, param_id, 
价值
) VALUES ( NAME_CONST('new_object_id',14), 1, '123')
其中 NAME_CONST 不是我期望看到的。我需要那里的整数值

如果我尝试使用 NEW.object_id 或 OLD.object_id 等变量 真正的 SQL 查询看起来像

INSERT INTO object_param_value_text (object_id, param_id, 
价值
) VALUES (NEW.object_id, 1, '123')

UPD1

我还尝试了

BEFORE UPDATE
AFTER UPDATE
两种方式从“新”变量中获取这个值。
NEW.object_id
我尝试在新声明的变量中设置然后使用它。
NEW.date1
我尝试在没有任何操作的情况下使用。

这是查询日志文件的结果

如您所见,声明的变量值是

NAME_CONST('new_object_id',14)
。并且
NEW.date1
变量不被视为变量。

<------><------>    42 Close stmt
<------><------>    42 Prepare<>UPDATE phone_client_item_1 SET cid=?, type=?, source_id=?, date1=?, date2=?,  comment=?, object_id=?, alias=? WHERE id=?
<------><------>    42 Execute<>UPDATE phone_client_item_1 SET cid=6968, type=1, source_id=7, date1=DATE'2021-01-13', date2=NULL,  comment='[LOCAL] ???? ?????', object_id=14, alias='' WHERE id=499
<------><------>    42 Query<-->INSERT INTO object_param_value_text (object_id, param_id, `value`) VALUES ( NAME_CONST('new_object_id',14), 1, NEW.date1) 
sql mysql triggers mariadb
1个回答
0
投票

没有。

使用

LAST_INSERT_ID()
。比在
information_schema
里翻找更简单、更安全。

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