Ich vermute, dass "reply id" bei Artikeln 0 und bei Kommentaren die Artikelnummer ist. Wenn das Ihr Design ist, sollte das funktionieren:
select * from yourTable
order by
case when "reply id" = 0 then id else "reply id" end, id
HINZUFÜGEN: Vielen Dank für die zusätzlichen Informationen in Ihrem Kommentar. Die Ergebnisse in die von Ihnen gewünschte Reihenfolge zu bringen, ist nicht so einfach, da der erste Ordnungsschlüssel das created_date des Thread-Startposts ist. Dieser steht nicht in der Datenzeile, so dass Sie einen Join benötigen. Hier ist meine beste Vermutung auf der Grundlage der zusätzlichen Informationen (die immer noch nicht vollständig genug sind, um mich vom Raten abzuhalten):
select
f.id, f.user_id, f.type, f.reply_id, f.text, f.url, f.created_date,
coalesce(parentfeed.created_date,f.created_date) as thread_date
from feed as f left outer join feed as parentfeed
on f.reply_id = parentfeed.id
order by
thread_date desc,
case when f.reply_id = 0 then 0 else 1 end,
created_date desc, id;
Möglicherweise müssen Sie die Syntax für Postgre anpassen. Ich habe dies in SQL Server getestet.
Wenn Sie damit immer noch nicht das erreichen, was Sie wollen, geben Sie bitte genau an, wie Sie die Daten zurückhaben wollen. Nennen Sie mir vorzugsweise die "id"-Reihenfolge, die ich für die Daten in Ihrer Dump-Datei sehen soll, und auch die Grundlage für diese Anordnung zu erläutern. Ich habe Folgendes getan:
-
Alle Nachrichten in einem Thread (Thread = eine Nachricht und ihre Kommentare) sollten in Gruppen zusammengefasst werden.
-
Innerhalb eines Themas steht die Nachricht an erster Stelle, gefolgt von den Kommentaren in umgekehrter chronologischer Reihenfolge. Das Thema mit dem jüngsten Erstellungsdatum sollte an erster Stelle stehen, dann das Thema mit dem zweitjüngsten Erstellungsdatum und so weiter. (Ihre Beispieldaten enthielten viele Kommentare mit demselben Erstellungsdatum, daher habe ich "id" als sekundären Ordnungsschlüssel für die Kommentare innerhalb eines Threads verwendet).
Nota: Ihr Dump zeigt, dass created_date auf CURRENT_TIMESTAMP aktualisiert wird, wenn ein Beitrag geändert wird. Wenn es sich um ein lebendes Forum handelt, sollten Sie sich bewusst sein, dass dies dazu führen kann, dass Kommentare datiert werden vor Das bedeutet, dass ein Thema an erster Stelle bleibt, wenn es häufig geändert wird (auch wenn sich der Text nicht ändert). (Das ist für meine Lösung nicht relevant, aber ich dachte, es sei erwähnenswert).
Da eine Verknüpfung erforderlich ist, wird diese Abfrage nun viel langsamer sein. Mein Vorschlag: Führen Sie zwei Datumsspalten, "thread_last_modified" und "item_last_modified". Sie müssen die Aktualisierungen von den Thread-Startern zu den Kommentaren kaskadieren, aber ich denke, es lohnt sich, wenn es nicht viele Aktualisierungen gibt, weil die Abfrage viel einfacher sein kann. Ich habe dies nicht getestet, weil es einige Änderungen an Ihrem Design erfordert:
select
id, user_id, type, reply_id, text, url, thread_last_modified, item_last_modified
from feed
order by
thread_last_modified desc,
case when f.reply_id = 0 then 0 else 1 end,
item_last_modified desc, id;
ZUSÄTZLICH #2 : Wenn Sie nur den Thread wollen, der den Kommentar mit der ID ::thisOne enthält, können Sie diese Zeile zwischen die ON- und ORDER BY-Klauseln einfügen (für meine erste zusätzliche Lösung, die Verknüpfung):
where parentfeed.id = (
select coalesce(reply_id,id)
from feed
where id = ::thisOne
)
Theoretisch sollte dieser Lookup nur einmal für die Abfrage ausgewertet werden, aber wenn das in der Praxis nicht der Fall ist, könnte man ihn als ::thisOneThreadID vorberechnen und hinzufügen
where parentfeed.id = ::thisOneThreadID
Für die zweite Lösung, vorausgesetzt, Sie rechnen wieder vor, versuchen Sie
where coalesce(id,reply_id) = ::thisOneThreadID
Übrigens vermute ich, dass beide meiner Lösungen Threads zusammenführen, die genau zur gleichen Zeit zuletzt geändert wurden...