I have a Messages table that looks like this:
Messages
+-----+------------+-------------+--------------+
| id | sender_id | receiver_id | created_at |
+-----------------------------------------------+
| 1 | 1 | 2 | 1/1/2013 |
| 2 | 1 | 2 | 1/1/2013 |
| 3 | 2 | 1 | 1/2/2013 |
| 4 | 3 | 2 | 1/2/2013 |
| 5 | 3 | 2 | 1/3/2013 |
| 6 | 5 | 4 | 1/4/2013 |
+-----------------------------------------------+
Where a 'thread' is a group of messages between a given sender_id and receiver_id I want a query to return the most recent 10 messages for the most recent 10 threads where either the sender_id or receiver_id is a given id.
Expected output where given user_id is 5:
+-----+------------+-------------+--------------+
| id | sender_id | receiver_id | created_at |
+-----------------------------------------------+
| 1 | 5 | 2 | 1/4/2013 |
| 2 | 5 | 2 | 1/4/2013 |
| 3 | 2 | 5 | 1/4/2013 |
| 4 | 3 | 5 | 1/4/2013 |
| 5 | 5 | 2 | 1/3/2013 |
| 6 | 5 | 4 | 1/3/2013 |
+-----------------------------------------------+
up to a limit of 10 messages between, for example, user 5 and 2 (above there are 4) and a limit of 10 threads (above there are 3).
I've been trying with this sort of query using a subquery but haven't managed to get the second limit on the number of distinct threads.
SELECT * FROM (SELECT DISTINCT ON (sender_id, receiver_id) messages.*
FROM messages
WHERE (receiver_id = 5 OR sender_id = 5) ORDER BY sender_id, receiver_id,
created_at DESC)
q ORDER BY created_at DESC
LIMIT 10 OFFSET 0;
I'm considering creating a new Thread table containing a thread_id field which would be the concatenation of sender_id + receiver_id and then just joining on Messages but I have a sneaky suspicion that it should be doable with just one table.