joe: Forum: Anzeigen wo neue Posts gemacht wurden

Hallo.

Ich code gerade ein kleines Forum.
Ich möchte gerne das man weiß, ob es seit dem letzten Besuch, neue Posts in einer Diskussion gibt.
Wenn diese Posts wo es was neues gibt z.B. blau hervorgehoben wird,
dann soll es so sein.
Jemand der noch nie in einer bestimmten Diskussion war, für den sind alle Diskussionen blau hervorgehoben.
Geht er herrein und wieder herraus, so wird diese grau statt blau dargestellt.
Wenn nun dort jemand einen Post macht, dann soll es wieder blau sein.

Wie setze ich sowas performant um?
Ich nutze PHP, JS und als Datenbank-Backend PostgreSQL.

Habt ihr ein paar Vorschläge?

Gruß, Joe

--
Add me here: cussit.com
Bei cussit.com bin ich aktiver als hier ;)
  1. Hi,

    ganz einfach, speichere für registrierte Benutzer, in welchen Threads (Diskussionen) sie bereits waren und wann. Wichtig dabei ist, dass du die Benutzer "identifizieren" kannst, mit Cookie z.b. (nur um eine Möglichkeit zu nennen). Wenn du die Threadübersicht aufbaust, ist es dann nicht mehr als eine Abfrage mit Join bzw eine "korrelierende" Abfrage mit einem extra-Feld à la "farbige Markierung". Diese Abfrage ist dann natürlich benutzerspezifisch. Für Benutzer, die sich nicht identifizieren lassen (weil sie sich z.b. nicht authentifizieren) wird das dann etwas komplizierter.

    Gruss, Frank

    1. Also ich würde das jetzt so machen nach deiner Anleitung:

      Hole die Uhrzeit des letzten Post aus dem Thread
      Hole die Uhrzeit des letzten Einsehens des Users in diesen Thread

      Falls Post > einsehen -> gib 1 zurück ansonsten 0

      Und im PHP Skript dann ($foo===0)?"blau":"weiß"

      Richtig?

      1. Ui. Ich hab da ganz große SQL-Lücken.

        Aktuell sieht der Query so aus:

        SELECT t1.threadid ,t1.threadtitel,t1.threadtype,t1.postcounter  
        FROM mainproject.board_thread AS t1  
        LEFT JOIN mainproject.board_category AS t2 ON categoryname='".$name."'  
        WHERE t1.categoryid=t2.categoryid  
        GROUP BY t1.threadid,t1.threadtitel,t1.threadtype,t1.postcounter  
        ORDER By postcounter
        

        Wie bekomme ich nun zusätzlich aus einer Tabelle X den letzten Eintrag wo ID=1 ist mit Hilfe eines Joins?

        Beispiel:
        Tabelle X
        id post creationtime
        1  few  timestamp von heute
        2  hfg  timestamp von gestern
        3  kiu  timestamp von vorgestern
        1  iop  timestamp von gestern

        Ich möchte also "timestamp von heute" auslesen.
        Wie bringe ich das oben in den Query ein?
        Bei JOINS stoße ich vor das Problem das ich nur boolsche Werte im ON Bereich raushaben darf. Also ON id=1 AND MAX(creationtime) geht nicht.
        Selbiges darf auch nicht in der WHERE Klausel stehen.

        Ich nutze PostgreSQL.

        Wie geht das nun? =/

        1. Bei JOINS stoße ich vor das Problem das ich nur boolsche Werte im ON Bereich raushaben darf. Also ON id=1 AND MAX(creationtime) geht nicht.

          Ein Problem ist es ja nicht wirklich ;-)
          Du sagst doch auch nicht "alle Datensätze bei denen Datum ist", sondern "alle Datensätze bei denen das Datum größer als der 3. Dezember ist".

          Sag dem SQL halt noch was mit MAX(creationtime) sein soll.

          1. Bei JOINS stoße ich vor das Problem das ich nur boolsche Werte im ON Bereich raushaben darf. Also ON id=1 AND MAX(creationtime) geht nicht.
            Ein Problem ist es ja nicht wirklich ;-)
            Du sagst doch auch nicht "alle Datensätze bei denen Datum ist", sondern "alle Datensätze bei denen das Datum größer als der 3. Dezember ist".

            Sag dem SQL halt noch was mit MAX(creationtime) sein soll.

            Verstehe ich nicht. Wo genau und was?

            Danke.lg.

            Joe

            1. Okay ich habs fast!

                
              SELECT t1.threadid ,t1.threadtitel,t1.threadtype,t1.postcounter , COUNT(t4.postid) AS numPosts  
              FROM mainproject.board_thread AS t1  
              LEFT JOIN mainproject.board_category AS t2 ON categoryname='".db::escape($tag)."'  
              LEFT JOIN mainproject.users_follow_disc AS t3 ON t3.uid=".$_SESSION['userid']." AND t3.tid=t1.threadid  
              LEFT JOIN mainproject.board_post AS t4 ON t4.creationtime > t3.thetime AND t4.threadid=t1.threadid  
              WHERE t1.categoryid=t2.categoryid  
              GROUP BY t1.threadid,t1.threadtitel,t1.threadtype,t1.postcounter  
              ORDER BY postcounter
              

              Nun. Jetzt liest er die Anzahl aller Posts aus irgendwie. Ich kann nicht genau definieren was er macht. Er gibt mir wenn ich einen neuen Post mache irgendwo, anschließend die Anzahl aller Posts in diesem Thread aus.
              Das Problem liegt denk ich hier:

              [1]
              LEFT JOIN mainproject.users_follow_disc AS t3 ON t3.uid=".$_SESSION['userid']." AND t3.tid=t1.threadid

              und hier

              [2]

                
              LEFT JOIN mainproject.board_post AS t4 ON t4.creationtime > t3.thetime AND t4.threadid=t1.threadid
              

              Denn bei [1] müsste die Ergebnismenge auf 1 reduziert werden, so das am Ende nur "das letzte mal als er die Diskussion angesehen hat" geliefert wird.
              In Form eines Subselects gehts nicht weil er dann die Threadid nicht hat, diese liegt ja in einer anderen Ebene und kommt aus t1.
              [2] müsste anschließend diesen Zeitpunkt bekommen (t3.thetime) muss also ersetzt werden.

              Hoffe du kannst mir helfen.

              Lg, Joe

              1. So ich habs jetzt so probiert.
                Weiter weiß ich wirklich nicht mehr.

                SELECT t1.threadid ,t1.threadtitel,t1.threadtype,t1.postcounter,MAX(thepost.thetime) AS lastpost  
                FROM mainproject.board_thread AS t1  
                  
                LEFT JOIN (SELECT t3.thetime,t3.tid  
                			 FROM mainproject.users_follow_disc AS t3  
                			 WHERE t3.uid=".$_SESSION['auth_userid']."  
                			 ORDER BY t3.thetime) AS thepost ON thepost.tid=t1.threadid  
                  
                LEFT JOIN mainproject.board_category AS t2 ON categoryname='".$tag."'  
                	  
                LEFT JOIN mainproject.board_post AS t4 ON t4.creationtime > lastpost AND t4.threadid=t1.threadid  
                  
                WHERE t1.categoryid=t2.categoryid  
                GROUP BY t1.threadid,t1.threadtitel,t1.threadtype,t1.postcounter  
                ORDER BY postcounter
                

                Er sagt leider das es lastpost nicht gäbe. Es steht halt oben in der SELECT KLausel =/.
                Hm .. wie komme ich nun an das Ergebnis mit der Maximalen Uhrzeit aus "thepost" ?

                1. Habs geschafft.

                  SELECT t1.threadid ,t1.threadtitel,t1.threadtype,t1.postcounter,COUNT(t4.postid) AS numPost  
                  FROM mainproject.board_thread AS t1  
                    
                  LEFT JOIN (SELECT DISTINCT ON (t3.tid) t3.tid,t3.thetime  
                  			 	FROM mainproject.users_follow_disc AS t3  
                  			 	WHERE t3.uid=".$_SESSION['userid']."  
                  				GROUP BY t3.thetime,t3.tid  
                  			 	ORDER BY t3.tid,t3.thetime) AS thepost  
                  ON thepost.tid=t1.threadid  
                    
                  LEFT JOIN mainproject.board_category AS t2 ON categoryname='".$tag."'  
                  	  
                  LEFT JOIN mainproject.board_post AS t4 ON t4.threadid=t1.threadid AND t4.creationtime > thepost.thetime  
                    
                  WHERE t1.categoryid=t2.categoryid  
                  GROUP BY t1.threadid,t1.threadtitel,t1.threadtype,t1.postcounter  
                  ORDER BY postcounter
                  

                  Und einen Fehler in der DB behoben das immer geupdatet wird wenn derjenige im thread war.