【问题标题】:MySQL get last Message (VarChar)MySQL 获取最后一条消息 (VarChar)
【发布时间】:2017-05-24 11:00:00
【问题描述】:

我正在尝试从某个线程获取最后一条消息,但似乎无法正确查询。 我似乎没有收到某个线程的最后一条消息。

简介

我使用 3 个表——message、message_users、message_threads

所有消息都属于某个线程(有点像论坛和帖子的工作方式?) 用户可以将多个用户添加到某个线程,因此多个用户可以在同一个线程中互相发送消息。

数据库结构

messages table
    id  |   t_id  |  u_id  |  message  |  time
--------+---------+--------+-----------+--------
      1 |    1    |   1    |  hello!   | timestamp
      2 |    1    |   2    |  hi!      | timestamp
      3 |    2    |   1    |  testing  | timestamp


message_threads
   id |  author |  subject  
------+---------+-----------
    1 |    1    | Subject 1  
    2 |    3    | Subject 2 
    3 |    2    | Subject 3


message_users
   id |   t_id  |  u_id  |  read  | nonotice
------+---------+--------+--------+----------
    1 |    1    |   1    |   0    |   0
    2 |    1    |   2    |   0    |   0
    3 |    2    |   1    |   1    |   0

查询

这是我正在使用的查询,它几乎可以正常工作,只是它没有得到最后一个 ID,也没有最后一条消息,有什么想法吗? (是的,我已经查看并搜索了有关此主题的先前问题,但无法根据答案以某种方式修复查询)

SELECT
  m2.message,
  mt.id AS thread_id,
  max(m.id) AS message_id, 
  max(m.time) AS time, 
  mt.subject
FROM message_users AS mu
LEFT JOIN message_threads AS mt ON mt.id = mu.t_id
LEFT JOIN message AS m  ON m.t_id = mt.id
INNER JOIN (
  select message as messages_text 
  from message group by t_id
) AS m2 ON m2.id = m.id
WHERE mu.u_id = 1 AND mu.read = 0 AND mu.nonotice = 0
GROUP BY mt.id
ORDER BY m.id DESC

【问题讨论】:

    标签: php mysql subquery messaging forum


    【解决方案1】:
    SELECT
      m.t_id,
      m.message,
      m.id AS max_message_id,
      m.ts AS max_message_ts,
      t.subject
    FROM messages AS m
    JOIN message_threads AS t ON m.t_id = t.id
    JOIN (
      SELECT t_id, max(id) max_id FROM messages GROUP BY 1
    ) AS m2 ON m.id = m2.max_id
    JOIN message_users AS u ON u.t_id = t.id AND u.u_id = 1 AND u.`read` = 0 AND u.nonotice = 0
    

    如果上面的 SQL 变慢了,你可以做以下任一操作:

    1 - 在内部连接 ​​SQL 中添加 where 以使结果更小,即:

    SELECT
      m.t_id,
      m.message,
      m.id AS max_message_id,
      m.ts AS max_message_ts,
      m2.subject
    FROM messages AS m
    JOIN (
      SELECT t.id, max(m.id) AS max_id, t.subject
      FROM messages AS m
      JOIN message_threads AS t ON m.t_id = t.id
      JOIN message_users AS u ON u.t_id = t.id 
         AND u.u_id = 1 AND u.`read` = 0 AND u.nonotice = 0
      GROUP BY 1
    ) AS m2 ON m.id = m2.max_id
    

    2 - 重新设计 message_thread 添加计算列:(last_message_id, last_updated) 等

    PS - 尽量避免使用 MySQL 关键字作为列名

    【讨论】:

    • 谢谢,我一回到家就试一试,如果有效我会更新。刚刚用额外的表格信息更新了问题。
    • 太棒了,它有效!使用第二个解决方案,因为第一个 oen 的结果为 0.05 秒,另一个 0.0009,也感谢您在命名约定方面的建议:)
    猜你喜欢
    • 2017-09-21
    • 2016-10-12
    • 1970-01-01
    • 1970-01-01
    • 2022-08-18
    • 1970-01-01
    • 2015-09-17
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多