在MySql中按不同方向对评论和回复进行排序

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

我在尝试对 Laravel 项目中的评论和回复(无限嵌套级别)进行排序时遇到麻烦。

我的表

comments
具有类似的结构(简化):
id
|
body
|
user_id
|
parent_id
|
commentable_id
|
created_at

(根)注释的

parent_id
具有 NULL 值。 单页评论和回复数量(
commentable_id
)可能会超过500条。

我希望能够对评论进行排序

created_at
DESC,但回复的树形结构应该保留。

到现在为止我有这个疑问:

WITH RECURSIVE child_comments (id, body, parent_id, created_at, path, depth) AS
(   
    SELECT id, body, parent_id, created_at,
        CAST(id AS CHAR(200)),
        0 as depth
    FROM comments
    WHERE 
        commentable_id = 150 
        AND parent_id is NULL
    UNION ALL 
    SELECT c.id, c.body, c.parent_id, c.created_at,
        CONCAT(cc.path, ', ', c.id),
        cc.depth + 1 
    FROM child_comments cc 
    JOIN comments c ON c.parent_id =cc.id
    WHERE c.commentable_id = 150
) SELECT * from child_comments
    ORDER BY
        CASE WHEN parent_id != 0 THEN path END,
        CASE WHEN parent_id is NULL THEN  `created_at` END DESC;

结果是这样的:

+------+------------------+-----------+---------------------+---------------+-------+
| id   | body             | parent_id | created_at          | path          | depth |
+------+------------------+-----------+---------------------+---------------+-------+
|    7 | coment 3         |      NULL | 2024-05-09 12:13:07 | 7             |     0 |
|    2 | coment 2         |      NULL | 2024-05-02 21:07:29 | 2             |     0 |
|    1 | coment 1         |      NULL | 2024-05-02 17:28:42 | 1             |     0 |
|    3 | coment 1_1       |         1 | 2024-05-07 23:02:50 | 1, 3          |     1 |
|    5 | coment 1_1_1     |         3 | 2024-05-07 23:03:02 | 1, 3, 5       |     2 |
|    6 | coment 1_1_1_1   |         5 | 2024-05-07 23:05:26 | 1, 3, 5, 6    |     3 |
|    9 | coment 1_1_1_1_1 |         6 | 2024-05-09 12:14:06 | 1, 3, 5, 6, 9 |     4 |
|    4 | coment 1_2       |         1 | 2024-05-07 23:02:57 | 1, 4          |     1 |
|    8 | coment 2_1       |         2 | 2024-05-09 12:13:35 | 2, 8          |     1 |
+------+------------------+-----------+---------------------+---------------+-------+

但我想要这样的结果:

+----+-------------------+-----------+---------------------+---------------+-------+
| id | body              | parent_id | created_at          | path          | depth |
+----+-------------------+-----------+---------------------+---------------+-------+
|  7 | comment 3         |      NULL | 2024-05-09 12:13:07 | 7             |     0 |
|  2 | comment 2         |      NULL | 2024-05-02 21:07:29 | 2             |     0 |
|  8 | comment 2_1       |         2 | 2024-05-09 12:13:35 | 2, 8          |     1 |
|  1 | comment 1         |      NULL | 2024-05-02 17:28:42 | 1             |     0 |
|  3 | comment 1_1       |         1 | 2024-05-07 23:02:50 | 1, 3          |     1 |
|  5 | comment 1_1_1     |         3 | 2024-05-07 23:03:02 | 1, 3, 5       |     2 |
|  6 | comment 1_1_1_1   |         5 | 2024-05-07 23:05:26 | 1, 3, 5, 6    |     3 |
|  9 | comment 1_1_1_1_1 |         6 | 2024-05-09 12:14:06 | 1, 3, 5, 6, 9 |     4 |
|  4 | comment 1_2       |         1 | 2024-05-07 23:02:57 | 1, 4          |     1 |
+----+-------------------+-----------+---------------------+---------------+-------+

有什么建议吗?

sql mysql
1个回答
0
投票

您可以在初始选择中添加

thread_created_at
并坚持所有子评论:

WITH RECURSIVE child_comments (id, body, parent_id, created_at, thread_created_at, path, depth) AS
(   
    SELECT id, body, parent_id, created_at, created_at,
        CAST(id AS CHAR(200)),
        0
    FROM comments
    WHERE 
        commentable_id = 150 
        AND parent_id IS NULL
    UNION ALL 
    SELECT c.id, c.body, c.parent_id, c.created_at, cc.thread_created_at,
        CONCAT(cc.path, ', ', c.id),
        cc.depth + 1 
    FROM child_comments cc 
    JOIN comments c ON c.parent_id = cc.id
    WHERE c.commentable_id = 150
)
SELECT * FROM child_comments
ORDER BY thread_created_at DESC, path ASC;

这是一个db<>小提琴

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