PostgreSQL
 sql >> Baza danych >  >> RDS >> PostgreSQL

Jak uzyskać najnowszą wiadomość w każdej rozmowie danego użytkownika w SQL?

Zakładając użytkowników o ID 1 i 3 , tak jak zrobiłeś na skrzypcach, interesuje nas wiadomość z najnowszym created_at i (sender_id, receiver_id) będąc (1,3) lub (3,1) .

Możesz użyć typów wierszy ad hoc, aby skrócić składnię:

SELECT * 
FROM   messages 
WHERE  (sender_id, receiver_id) IN ((1,3), (3,1))
ORDER  BY created_at DESC
LIMIT  1;

Lub wprost (i nieco szybciej, a także łatwiejszy w użyciu z indeksami):

SELECT * 
FROM   messages 
WHERE (sender_id = 1 AND receiver_id = 3 OR
       sender_id = 3 AND receiver_id = 1)
ORDER  BY created_at DESC
LIMIT  1;

Dla wszystkich rozmowy użytkownika

Dodano rozwiązanie zgodnie z prośbą w komentarzu.

SELECT DISTINCT ON (user_id) *
FROM (
   SELECT 'out' AS type, id, receiver_id AS user_id, body, created_at
   FROM   messages 
   WHERE  sender_id = 1

   UNION  ALL
   SELECT 'in' AS type, id, sender_id AS user_id, body, created_at
   FROM   messages 
   WHERE  receiver_id = 1
   ) sub
ORDER  BY user_id, created_at DESC;

Podejście tutaj polega na złożeniu obcego nadawcy / odbiorcy w jedną kolumnę, aby uprościć wyodrębnianie ostatniego wiersza.

Szczegółowe wyjaśnienie dla DISTINCT ON w tej powiązanej odpowiedzi:
Wybrać pierwszy wiersz w każdej grupie GROUP BY?

-> Zaktualizowano SQLfiddle .

Weź również pod uwagę ulepszony i uproszczony przypadek testowy w skrzypcach.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Railsy 3 ignorują wyjątek unikatowego ograniczenia Postgresa

  2. Jak utworzyć sumę kroczącą okresu rozliczeniowego

  3. Czy istnieje sposób na zdefiniowanie nazwanej stałej w zapytaniu PostgreSQL?

  4. Połączenie łańcuchowe nie filtruje zgodnie z oczekiwaniami

  5. Jak używać indeksu w obcej tabeli zapytania SELECT MAX(id) w PostgreSQL?