列出所有用户按对话排序的消息
List messages ordered by conversations for all users
我的用例是一个管理视图,用于查看数据库中的所有消息。
我想要一个按对话和开始日期排序的消息列表,目的是能够在其上下文中查看每条消息。
对话是两个用户之间互动的列表。
我没有conversation
table,只有message
table。
来自这个数据样本:
id sender recipient
--------------------------
1 marc rémi
2 gépéto sylvain
3 rémi marc
4 julie georgette
5 rémi marc
6 denis julie
7 julie rémi
8 sylvain gépéto
9 denis marc
10 denis julie
我想获得:
id sender recipient
--------------------------
1 marc rémi
3 rémi marc
5 rémi marc
2 gépéto sylvain
8 sylvain gépéto
4 julie georgette
6 denis julie
10 denis julie
7 julie rémi
9 denis marc
目前,我只是希望获得每次对话的第一条消息,作为实现预期结果的第一步:
SELECT message.id, message.sender , message.recipient
FROM message
GROUP BY message.sender, message.recipient
HAVING message.id = min(message.id)
ORDER BY message.id DESC;
但我做错了,对于所有双向对话,我得到了两个对话,而不是一个对话:
id sender recipient
--------------------------
8 sylvain gépéto
2 gépéto sylvain
所以,我被困在这里......我会很感激一些提示!
SELECT m.*, CASE
WHEN sender <= recipient THEN concat(sender,'-',recipient)
ELSE concat(recipient,'-', sender)
END as conversation
FROM message m
ORDER BY conversation, id
输出
| id | sender | recipient | conversation |
|----|---------|-----------|-----------------|
| 6 | denis | julie | denis-julie |
| 10 | denis | julie | denis-julie |
| 9 | denis | marc | denis-marc |
| 4 | julie | georgette | georgette-julie |
| 2 | gépéto | sylvain | gépéto-sylvain |
| 8 | sylvain | gépéto | gépéto-sylvain |
| 7 | julie | rémi | julie-rémi |
| 1 | marc | rémi | marc-rémi |
| 3 | rémi | marc | marc-rémi |
| 5 | rémi | marc | marc-rémi |
这是第一个方法,如果您需要 marc-rémi
是第一个,您需要添加另一个 select 以获得每个对话的 MIN()
。
SELECT conversation_id, T.id, T.sender, T.recipient, T.conversation
FROM (
SELECT CASE
WHEN sender <= recipient THEN concat(sender,'-',recipient)
ELSE concat(recipient,'-', sender)
END as conversation,
MIN(id) as conversation_id
FROM message m
GROUP BY conversation
) as convesation_start
JOIN (
SELECT m.*, CASE
WHEN sender <= recipient THEN concat(sender,'-',recipient)
ELSE concat(recipient,'-', sender)
END as conversation
FROM message m
) as T
ON
convesation_start.conversation = T.conversation
ORDER BY conversation_id, T.id
输出
| conversation_id | id | sender | recipient | conversation |
|-----------------|----|---------|-----------|-----------------|
| 1 | 1 | marc | rémi | marc-rémi |
| 1 | 3 | rémi | marc | marc-rémi |
| 1 | 5 | rémi | marc | marc-rémi |
| 2 | 2 | gépéto | sylvain | gépéto-sylvain |
| 2 | 8 | sylvain | gépéto | gépéto-sylvain |
| 4 | 4 | julie | georgette | georgette-julie |
| 6 | 6 | denis | julie | denis-julie |
| 6 | 10 | denis | julie | denis-julie |
| 7 | 7 | julie | rémi | julie-rémi |
| 9 | 9 | denis | marc | denis-marc |
您可以使用以下查询获取每个对话的第一条消息的id
:
SELECT MIN(id),
IF(sender > recipient, sender, recipient) AS participantA,
IF(sender > recipient, recipient, sender) AS participantB
FROM message
GROUP BY participantA, participantB
现在在派生的 table 中使用上述查询以获得所需的结果:
SELECT id, sender, recipient
FROM (
SELECT id, sender, recipient,
IF(sender > recipient, sender, recipient) AS participantA,
IF(sender > recipient, recipient, sender) AS participantB
FROM message) AS t1
INNER JOIN (
SELECT MIN(id) AS minId,
IF(sender > recipient, sender, recipient) AS participantA,
IF(sender > recipient, recipient, sender) AS participantB
FROM message
GROUP BY participantA, participantB
) AS t2 ON t1.participantA = t2.participantA AND t1.participantB = t2.participantB
ORDER BY t2.minId
我想到了这个:
SELECT id, sender, recipient
FROM (SELECT message.id, message.sender , message.recipient
,concat(greatest(message.sender,message.recipient)
,least(message.sender,message.recipient)
) as conv
FROM message) as tab1
INNER JOIN
(SELECT min(id) as min
,concat(greatest(message.sender,message.recipient)
,least(message.sender,message.recipient)
) as conv
FROM message
GROUP BY conv) as tab2
ON tab1.conv = tab2.conv
ORDER BY tab2.min
- 其中 conv 是每对夫妇的标识符
我的用例是一个管理视图,用于查看数据库中的所有消息。
我想要一个按对话和开始日期排序的消息列表,目的是能够在其上下文中查看每条消息。
对话是两个用户之间互动的列表。
我没有conversation
table,只有message
table。
来自这个数据样本:
id sender recipient
--------------------------
1 marc rémi
2 gépéto sylvain
3 rémi marc
4 julie georgette
5 rémi marc
6 denis julie
7 julie rémi
8 sylvain gépéto
9 denis marc
10 denis julie
我想获得:
id sender recipient
--------------------------
1 marc rémi
3 rémi marc
5 rémi marc
2 gépéto sylvain
8 sylvain gépéto
4 julie georgette
6 denis julie
10 denis julie
7 julie rémi
9 denis marc
目前,我只是希望获得每次对话的第一条消息,作为实现预期结果的第一步:
SELECT message.id, message.sender , message.recipient
FROM message
GROUP BY message.sender, message.recipient
HAVING message.id = min(message.id)
ORDER BY message.id DESC;
但我做错了,对于所有双向对话,我得到了两个对话,而不是一个对话:
id sender recipient
--------------------------
8 sylvain gépéto
2 gépéto sylvain
所以,我被困在这里......我会很感激一些提示!
SELECT m.*, CASE
WHEN sender <= recipient THEN concat(sender,'-',recipient)
ELSE concat(recipient,'-', sender)
END as conversation
FROM message m
ORDER BY conversation, id
输出
| id | sender | recipient | conversation |
|----|---------|-----------|-----------------|
| 6 | denis | julie | denis-julie |
| 10 | denis | julie | denis-julie |
| 9 | denis | marc | denis-marc |
| 4 | julie | georgette | georgette-julie |
| 2 | gépéto | sylvain | gépéto-sylvain |
| 8 | sylvain | gépéto | gépéto-sylvain |
| 7 | julie | rémi | julie-rémi |
| 1 | marc | rémi | marc-rémi |
| 3 | rémi | marc | marc-rémi |
| 5 | rémi | marc | marc-rémi |
这是第一个方法,如果您需要 marc-rémi
是第一个,您需要添加另一个 select 以获得每个对话的 MIN()
。
SELECT conversation_id, T.id, T.sender, T.recipient, T.conversation
FROM (
SELECT CASE
WHEN sender <= recipient THEN concat(sender,'-',recipient)
ELSE concat(recipient,'-', sender)
END as conversation,
MIN(id) as conversation_id
FROM message m
GROUP BY conversation
) as convesation_start
JOIN (
SELECT m.*, CASE
WHEN sender <= recipient THEN concat(sender,'-',recipient)
ELSE concat(recipient,'-', sender)
END as conversation
FROM message m
) as T
ON
convesation_start.conversation = T.conversation
ORDER BY conversation_id, T.id
输出
| conversation_id | id | sender | recipient | conversation |
|-----------------|----|---------|-----------|-----------------|
| 1 | 1 | marc | rémi | marc-rémi |
| 1 | 3 | rémi | marc | marc-rémi |
| 1 | 5 | rémi | marc | marc-rémi |
| 2 | 2 | gépéto | sylvain | gépéto-sylvain |
| 2 | 8 | sylvain | gépéto | gépéto-sylvain |
| 4 | 4 | julie | georgette | georgette-julie |
| 6 | 6 | denis | julie | denis-julie |
| 6 | 10 | denis | julie | denis-julie |
| 7 | 7 | julie | rémi | julie-rémi |
| 9 | 9 | denis | marc | denis-marc |
您可以使用以下查询获取每个对话的第一条消息的id
:
SELECT MIN(id),
IF(sender > recipient, sender, recipient) AS participantA,
IF(sender > recipient, recipient, sender) AS participantB
FROM message
GROUP BY participantA, participantB
现在在派生的 table 中使用上述查询以获得所需的结果:
SELECT id, sender, recipient
FROM (
SELECT id, sender, recipient,
IF(sender > recipient, sender, recipient) AS participantA,
IF(sender > recipient, recipient, sender) AS participantB
FROM message) AS t1
INNER JOIN (
SELECT MIN(id) AS minId,
IF(sender > recipient, sender, recipient) AS participantA,
IF(sender > recipient, recipient, sender) AS participantB
FROM message
GROUP BY participantA, participantB
) AS t2 ON t1.participantA = t2.participantA AND t1.participantB = t2.participantB
ORDER BY t2.minId
我想到了这个:
SELECT id, sender, recipient
FROM (SELECT message.id, message.sender , message.recipient
,concat(greatest(message.sender,message.recipient)
,least(message.sender,message.recipient)
) as conv
FROM message) as tab1
INNER JOIN
(SELECT min(id) as min
,concat(greatest(message.sender,message.recipient)
,least(message.sender,message.recipient)
) as conv
FROM message
GROUP BY conv) as tab2
ON tab1.conv = tab2.conv
ORDER BY tab2.min
- 其中 conv 是每对夫妇的标识符