简体   繁体   English

事务语法错误,想回滚删除

[英]Transaction syntax error, want to roll back delete

Ok I changed to MCRE....好的,我改为MCRE....

CREATE TABLE id INT user_id INT updated_at DATE

Example Data...示例数据...

id user_id updated_at

1 20 2019-09-02 01:00:00

2 20 2019-09-03 04:00:00

3 22 2019-09-04 03:00:00

4 22 2019-09-05 05:00:00

5 20 2019-09-10 01:00:00

I want to keep 1 row per user and just most recently updated, and put it in rollback to test.我想为每个用户保留 1 行并且最近更新,然后将其回滚以进行测试。

BEGIN TRANSACTION;
DELETE FROM table
    WHERE id NOT IN (
        SELECT a.id FROM (
            SELECT id, MAX(updated_at) FROM table GROUP BY user_id)
        a);
END TRANSACTION;

mysql Ver 8.0.18 for macos10.?? on x86_64 (MySQL Community Server - GPL)

Consider the following (slightly modified, by way of example):考虑以下内容(略作修改,例如):

DROP TABLE IF EXISTS my_table;

CREATE TABLE my_table
(id SERIAL PRIMARY KEY
,user_id INT NOT NULL
,updated_at DATE NOT NULL
);

INSERT INTO my_table VALUES
(1,20,'2019-09-22 01:00:00'),
(2,20,'2019-09-13 04:00:00'),
(3,22,'2019-09-14 03:00:00'),
(4,22,'2019-09-05 05:00:00'),
(5,22,'2019-09-20 01:00:00');

SELECT id, MAX(updated_at) n FROM my_table GROUP BY user_id;
+----+------------+
| id | n          |
+----+------------+
|  1 | 2019-09-22 |
|  3 | 2019-09-20 |
+----+------------+

There is no row in the data set with an id of 3, and an updated_at of '2019-09-20 01:00:00'.数据集中没有 id 为 3 且 updated_at 为 '2019-09-20 01:00:00' 的行。 That is what I mean by nonsensical.这就是我所说的荒谬。

The following is an example of a valid query:以下是有效查询的示例:

SELECT user_id, MAX(updated_at) n FROM my_table GROUP BY user_id;

This can then be used (for instance) within a subquery...然后可以在子查询中使用(例如)...

SELECT a.*
  FROM my_table a
  JOIN 
     ( SELECT user_id
            , MAX(updated_at) updated_at
         FROM my_table 
        GROUP 
           BY user_id
     ) b
    ON b.user_id = a.user_id 
   AND b.updated_at = a.updated_at;

You could use the above to create a new table with just the data you wished to retain.您可以使用上述内容创建一个仅包含您希望保留的数据的新表。 If feasible, then this approach is typically orders of magnitude faster then a DELETE.如果可行,那么这种方法通常比 DELETE 快几个数量级。

您应该尝试 COMMIT TRANSACTION 而不是 END TRANSACTION

  • Change END TRANSACTION with ROLLBACK .使用ROLLBACK更改END TRANSACTION
  • Change BEGIN TRANSACTION with START TRANSACTION ( BEGIN is an alias, BEGIN TRANSACTION is nothing).使用START TRANSACTION更改BEGIN TRANSACTIONBEGIN是别名, BEGIN TRANSACTION什么都不是)。

See MySQL documentation for transaction statements .有关事务语句,请参阅MySQL 文档

START TRANSACTION;
DELETE FROM table
    WHERE id NOT IN (
        SELECT a.id FROM (
            SELECT id, MAX(updated_at) FROM table GROUP BY user_id)
        a);
ROLLBACK;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM