[PHP/MySQL] Online Status

web2null

ehem. assactions
ID: 131418
L
20 April 2006
1.775
165
Hallo, ich wollte ein script schreiben das mir den online status eines users anzeigt, d.h. wenn ein user inerhalb der letzten 5 min nicht auf der seite https://xyz.de/index.php?online=1 war, das sich automatisch in der Datenbank der eintrag des user online=0 setzt
 
Ganz einfach.

Wenn der User sich einloggt wird ein Eintrag in die DB gemacht.
Bei jedem weiteren Klick, also wenn der User sich von Seite zu Seite klickt, wird das Datum aktualisiert.

Und bei jedem Aufruf wird geprüft ob es Einträge gibt die älter x minuten sind.

Hoffe das hilft Dir.

MfG
Greaseball100
 
also muss ich das so machen das bei jedem user überprüft wird ob es eine zeit älter als 5 min gibt? Is das nciht ne menge träffic zusätzlich? Kann man das nicht so machen das wenn der user das Browser Fenster schliest das der eintrag in der DB auf 9 gesetzt wird

das problem ist der user kann nur auf der eine seite surfen also ncihts mit klicken
 
Kann man das nicht so machen das wenn der user das Browser Fenster schliest das der eintrag in der DB auf 9 gesetzt wird
Das geht nicht. Du kriegst nicht mit, ob das Fenster offen is.
Alles, was du aus Serverseite "hörst", ist ein Request "Gib mir Seite Xyz". Ob die Seite wirklich angezeigt wird, blockiert wird, umgeändert wird oder was auch immer, kriegst du nicht mit.

Du kannst also nur 100%ig sagen: Wenn der Request da is, hockt der User am Rechner. Danach weißt du nichts.

Für solche Online-Status bleibt dir also nur die Möglichkeit - wie schon angesprochen -, immer die Zeit zu speichern, wenn der Request eingeht. Und wenn du wissen willst, ob der User noch on is, subtrahiere die aktuelle Zeit von der des letzten Requests. Ist die Differenz größer als eine vorgegebene Schranke (Bsp. klamm-Forum: 15min), ist der User offline, sonst vermutest du, er sei online.

Traffic macht das nicht. Traffic is ja nur die Datenmenge Request+Response.

edit:
Du könntest via AJAX alle paar Sekunden einen Ping zum Server senden. Aber das funktioniert nicht 100%ig, da Abhängigkeit von JavaScript und schlimmer: das kostet kräftig Traffic, weil jeder Ping ja einen Request sendet.
 
Zuletzt bearbeitet:
theHacker schrieb:
Das stimmt so nicht ganz. Ich habe gerade mal geschaut mit meinem FF 3.xx funktioniert folgendes bei Klick auf einen Link, schließen des Tabs und generelles verlassen der Seite durch zB Back Button.

In wie weit der IE da noch mitspielt müsste man testen.

Aber der Grundsatz des aktivierten JS ist trotzdem noch gegeben.
 
Erst mal grundsätzlich.

HTML, Javascript und Co. läuft Clientseitig.

PHP,ASP usw Serverseitig.

Ein Useronline Script läuft immer Serverseitig.
Es vermerkt in der DB wann der Request eingegangen ist und prüft ob es Einträge in der DB gibt die über dem Zeitlimit liegen.

Was FF oder IE macht interresiert in diesem Moment nicht.
 
@strolch00:
Das entspricht meinem "Ping", ja. JavaScript muss aktiviert sein und zusätzlicher Traffic entsteht.

Ich muss sagen, ich hab noch keine Seite gesehen, die versucht, sekundengenau den Onlinestatus zu bestimmen. Es wird alles mit Idle-Zeit gemacht. Idlet ein User zu lange, ist er definitionsmäßig nach x Minuten offline.
 
Und selbst wenn es eine gute Möglichkeit gäbe, den User auf offline zu schalten, wenn er die Seite verlässt, macht das Sinn?

Wenn ich deine Seite noch in nem Tab offen habe, und meinen Rechner anlasse und sonstwohin gehe ist die Seite noch offen, aber ich würde mich definitiv nicht als online bezeichnen.
 
ok alles klar dann werde ich das wohl mit einem update der zeit machen, wie könnte ich das am besten anstellen, ich kann ja nicht

date("h:i:s") < date("h:i:s") + "5 minutes"

kann mir einer n tip geben?
 
Hier eine Idee, die ich aber selbst nicht ausprobiert habe. Die Lösung erfordert aktiviertes Javascript.

Aufbauend auf dem Ansatz von strolch00 kannst du vor dem endgültigen Verlassen der Seite einen Request ausführen.
Details dazu siehe https://de.wikipedia.org/wiki/XMLHttpRequest

Damit könntest du also folgendes machen:
1) Beim Aufbau der Seite trägst du eine Satz in die DB ein. Dieser enthält einen Startzeitpunkt.
2) Im Unload rufst du einen Request auf, der den im Schritt (1) angelegten Satz um ein Endetimestamp ergänzt.

Schritt (2) kann aus mehreren Gründen nicht zustanden kommen.
z.B.: Internetverbindung wurde vor Verlassen der Seite gekappt, ...

Bei der Interpretation mußt du einiges berücksichtigen:
* User arbeiten oft mit mehreren offenen Seiten gleichzeitig
* Browser haben eine Cache
* User stehen auf und gehen zum Kühlschrank, auf WC, ...
 
ok alles klar dann werde ich das wohl mit einem update der zeit machen, wie könnte ich das am besten anstellen, ich kann ja nicht

date("h:i:s") < date("h:i:s") + "5 minutes"

kann mir einer n tip geben?
Code:
SELECT * FROM db WHERE time >= UNIX_TIMESTAMP() - 300


Bei der Interpretation mußt du einiges berücksichtigen:
* User arbeiten oft mit mehreren offenen Seiten gleichzeitig
* Browser haben eine Cache
* User stehen auf und gehen zum Kühlschrank, auf WC, ...
womit wir wieder bei dem normalen "Timeout"-Problem wären.
Das einzige, was deine Lösung bewirkt ist für User mit nur einem Tab pro Domain die Zeit exakter zu berechnen, für Leute die in vielen Tabs arbeiten komplett falsche Daten zu liefern.
 
Ein UNIX-Timestamp ist die Anzahl der Sekunden, die seit "UNIX-Null" (1.1.1970 0:00:00 UTC) vorgangen sind.

Wenn du also zwei Timestamps voneinander subtrahierst, kommen Sekunden raus. Ja.
 
300 Sekunden, also 5 Minuten.

Wenn man mit Datenbanken arbeitet sollte man sich in SQL wenigstens bisschen auskennen :D
 
Nein. UNIX-Timestamps sind für MySQL nur stinknormale Integer. Die Bedeutung, dass es sich um eine Zeit handelt, ordnet ja nur der Programmierer zu.

Du kannst aber mit echten Daten in MySQL ganz normal rechnen:
Code:
[FONT=Courier New][B][COLOR=#9932cc]SELECT[/COLOR][/B] something [B][COLOR=#9932cc]FROM[/COLOR][/B] tbl_name
[B][COLOR=#9932cc]WHERE[/COLOR][/B] [B][COLOR=#9932cc]DATE_SUB[/COLOR][/B][COLOR=#9932cc]([/COLOR][COLOR=DarkOrchid][B]CURDATE[/B]([/COLOR][COLOR=DarkOrchid])[/COLOR], [B][COLOR=#9932cc]INTERVAL[/COLOR][/B] [COLOR=DarkOrchid][COLOR=black]30[/COLOR] [B]DAY[/B])[/COLOR] <= date_col;[/FONT]
siehe https://dev.mysql.com/doc/refman/5.1/de/date-and-time-functions.html
 
Hab sowas auch mal Programmiert.
Ist eigentlich ganz Simpel:

Braucht ne SQL Tabelle mit 2 Spalten:
1. Username/IP-Adresse
2. Letzte Aktivität des Users

Nun bindest du einfach in jede deiner Seiten mit dem include() Befehl eine PHP-Datei ein, die in die Tabelle schreibt.

Paar Tipps:
IP-Adresse bekommt man so:
Code:
$IP=$_SERVER['REMOTE_ADDR'];
Unix Timestamp wirst du so finden:
Code:
$timestamp=time();

Nun brauchst du ja nur noch ein Script, dass die Daten auswertet.
Das kann ich dir leider nicht vorkauen sondern nur tipps geben:

-mysql_result([RESSOURCE STRING],[ROW],[COL]) musst du benutzen
-Die For schleife sollte benutzt werden

Du musst einfach jede Spalte durchgehen und den timestamp der dort gespeichert ist Minus den aktuellen (neuen) timestamp rechnen. Ist das Ergebnis unter 300 wird der user angezeigt, anderenfalls nicht ^.^
 
-mysql_result([RESSOURCE STRING],[ROW],[COL]) musst du benutzen
-Die For schleife sollte benutzt werden

Du musst einfach jede Spalte durchgehen und den timestamp der dort gespeichert ist Minus den aktuellen (neuen) timestamp rechnen. Ist das Ergebnis unter 300 wird der user angezeigt, anderenfalls nicht ^.^
Diese Tipp vergiss bitte mal schnell 8O

Du rufst doch nicht alles ab, um dann PHP damit zu beschäftigen, rauszufinden, welche Datensätze du brauchst. Da brauchts keine for-Schleife (welche Spalten? Gibt doch nur eine: die Zeit der letzten Aktivität).
 
Jetzt wird mir erst einiges klar -.-
Ich hab das bei meinem Script auch so gemacht.
Dabei habe ich garnicht dran gedacht wie man es für den Server schonender machen kann ^.^

Ehm ja hier eine Verbesserung:

-Man ruft immer die Aktuelle Zeit ab
-Man Hängt an die SQL SELECT Anfrage am Ende ein WHERE an.
Man sucht einfach jeden Wert, der unter Timestamp+300 ist.
 
Ehm ja hier eine Verbesserung:

-Man ruft immer die Aktuelle Zeit ab
-Man Hängt an die SQL SELECT Anfrage am Ende ein WHERE an.
Man sucht einfach jeden Wert, der unter Timestamp+300 ist.
Genauso gehts. Das steht in verschiedenen Varianten jetzt schon 4x im Thread :mrgreen: