Welcher http-Statuscode soll verwendet werden, um dem Client mitzuteilen, dass die Sitzung abgelaufen ist?

79

Auf einer Webseite werden YAX-Verbindungsmanager / Datenquelle verwendet, um AJAX-Anforderungen an den Server zu senden. Wenn für die Sitzung (die Informationen darüber enthält, ob der Benutzer authentifiziert wurde) bereits eine Zeitüberschreitung aufgetreten ist, werden diese Ajax-Antworten nur von authentifiziert angezeigt Benutzer sollten einen http-Statuscode zurückgeben, der dem Client mitteilt, dass die Sitzung bereits abgelaufen ist. Der Client leitet ihn dann entweder einfach zur Anmeldeseite weiter oder fragt ihn, ob er die Sitzung verlängern möchte.

Meine Frage ist, welcher http-Statuscode in dieser Situation am besten geeignet ist, um dem Client mitzuteilen, dass die Sitzung abgelaufen ist.

Liste der HTTP-Statuscodes aus dem Wiki

Bobo
quelle
Möchten Sie den Benutzer warnen, dass die Sitzung bald abläuft, damit der Benutzer etwas tun kann, um sie zu erneuern? In diesem Fall müsste dies von einem Timer in JavaScript verarbeitet werden, der vor dem Sitzungszeitlimit auf dem Server ausgelöst wird. Zu dem Zeitpunkt, an dem der Statuscode vom Server gesendet wird, wäre er bereits abgelaufen. Ein Timer wäre auch erforderlich, wenn Sie sie automatisch auf eine andere Seite umleiten würden, wenn sie die Seite im Leerlauf belassen würden.
Jason
8
Na ja, 418 natürlich! Kurz und kräftig ...
Tim Post
Vaadin verwendet 410 Gone, aber da es vom Browser zwischengespeichert werden kann, würde ich es nicht empfehlen
sreg

Antworten:

65

Das Beste, was ich vorschlagen kann, ist ein HTTP 401-Statuscode mit einem WWW-Authenticate-Header.

Das Problem bei 403- Anforderungen ist, dass der RFC 2616 angibt, dass die Autorisierung nicht hilft und die Anforderung NICHT wiederholt werden sollte. (dh egal, ob Sie authentifiziert sind oder nicht, Sie werden niemals Zugriff auf diese Ressource erhalten).

Das Problem mit 401- Anfragen besteht darin, dass sie "ein WWW-Authenticate-Header-Feld enthalten MÜSSEN". Wie jemand bemerkt hat, scheint es nicht gegen die Spezifikation zu verstoßen, einen benutzerdefinierten Wert in einem WWW-Authenticate-Header zu verwenden.

Ich kann keinen Grund dafür sehen RFC 2617 warum ein HTTP 401-Status in Kombination mit einem benutzerdefinierten WWW-Authenticate-Header wie diesem nicht in Ordnung wäre:

WWW-Authenticate: MyAuthScheme realm="http://example.com"

Das oAuth-Spezifikation scheint genau dies zu tun, da sie dies empfiehlt (obwohl sie meiner Meinung nach eine seltsame Interpretation des RFC haben):

WWW-Authenticate: OAuth realm="http://server.example.com/"

Dies scheint vom RFC nicht speziell SANKTIONIERT zu sein, aber ich kann nicht sehen, dass es dadurch verboten ist (es scheint nicht im Widerspruch zu einer Bedingung zu stehen, die MUSS oder MUSS NICHT, SOLLTE oder SOLLTE NICHT).

Ich wünschte, es gäbe einen spezifischeren HTTP-Statuscode für Zeitüberschreitungen und für Dinge wie CSRF-Token, die ungültig sind, damit dies klarer wird.

Iain Collins
quelle
34

Ich würde ein HTTP 401 empfehlen.

Während ein 403 im Grunde sagt: "Du darfst nicht, geh weg und komm nicht zurück", sagt ein 401: "Wir wissen nicht, ob du erlaubt bist oder nicht, weil du deinen Ausweis nicht mitgebracht hast. Geh Hol es dir und versuche es erneut. "

Vergleichen Sie die Definitionen von Wikipedia :

HTTP 403 - Die Anfrage war eine legale Anfrage, aber der Server weigert sich, darauf zu antworten.

HTTP 401 - Ähnlich wie 403 Verboten, jedoch speziell zur Verwendung, wenn eine Authentifizierung möglich ist, diese jedoch fehlgeschlagen ist oder noch nicht bereitgestellt wurde.

Jonathon Hill
quelle
3
401 ist für die HTTP-Authentifizierung vorgesehen . RFC 2616 sagt response MUST include a WWW-Authenticate header field. Es ist also falsch , diesen Code ohne ein WWW-Authenticate-Headerfeld zu senden .
Toxalot
18

Was ist mit 419 - es ist kein Standard, aber die Beschreibung auf Wikipedia scheint zu passen:

419 Zeitlimit für Authentifizierung

419 Authentication Timeout ist kein Teil des HTTP-Standards und zeigt an, dass die zuvor gültige Authentifizierung abgelaufen ist. Es wird als Alternative zu 401 Unauthorized verwendet, um zu unterscheiden, dass ansonsten authentifizierten Clients der Zugriff auf bestimmte Serverressourcen verweigert wird.

John Reichert
quelle
14
Irgendeine Idee, woher das kommt (außer Wikipedia)? Wenn es nicht im offiziellen RFC ist, wer hat es definiert?
Anaximander
5
Es scheint auch von dieser Wiki-Seite entfernt zu sein
Salem Ouerdani
Dies ist kein Teil der Spezifikation und auch nicht in Java HttpServletResponse@John verfügbar, wenn Sie eine andere zuverlässige Quelle kennen. Es ist besser, darauf zu verweisen.
Vishrant
Ich scheine nur in PHP Laravel
TroySteven
12

Ich glaube, der entsprechende Code wird 403 / Verboten sein. Es gibt keine, die in direktem Zusammenhang mit Sitzungen stehen.

Jason
quelle
1
Absolut das ist die richtige Antwort. Da die Sitzung abgelaufen ist, ist die Anforderung verboten, daher ist dies die beste Wahl.
März
3
403 teilt dem Client (im Grunde) mit, "Tun Sie das nicht noch einmal, es sei denn, Sie ändern Ihre Anfrage", aber wenn die Sitzung eingerichtet wurde, wäre keine Änderung erforderlich. Darüber hinaus können Sie in den meisten Fällen nichts mit der (aktuellen) Anforderung tun, um die Sitzung wiederherzustellen.
Tim Post
1
Genau! 401 wäre besser, denke ich, aber es erfordert eine HTTP-Authentifizierung. Ich denke, dies erfordert einen neuen Status in Anlehnung an 401 + 303 (also offensichtlich 704), der "Nicht autorisiert, siehe Andere, um Autorisierung zu erhalten" bedeutet. Zusätzlich dazu, dass es semantisch korrekter ist, könnte es auch die HTTP-Lösung für die Trampolin-Umleitung sein Ziel.
Anthony
5
Ich kann dem nicht zustimmen. RFC 2616 gibt ausdrücklich an, dass Anforderungen, die zu einer 403-Antwort führen, vom Client "NICHT wiederholt werden sollten" und dass "Autorisierung nicht hilft".
Iain Collins
5
authorization will not help- Ich verstehe das so, dass die HTTP-Authentifizierung nicht hilft. Welches ist richtig. Das Senden eines Autorisierungsheaders ändert nichts. Weder 401 noch 403 sind ideal, aber ich denke, 403 ist besser als 401. 401 ist falsch für das Sitzungszeitlimit, da RFC 2616 explizit angibt client MAY repeat the request with a suitable Authorization header field. In diesem Fall sollte der Client die Anforderung jedoch NICHT wiederholen (zumindest nicht ohne einen Zwischenschritt). Leider können wir den letzten Teil nicht mit einem Statuscode kommunizieren.
Toxalot
11

Die Wahrheit ist, dass es keinen Standard-HTTP-Statuscode für ein Sitzungszeitlimit gibt. Sitzungen werden in der Anwendungsschicht implementiert, nicht in der HTTP-Transportschicht.

Es gibt einen benutzerdefinierten Statuscode, den Microsoft für das Sitzungszeitlimit verwendet hat: 599, oder erstellen Sie einfach Ihren eigenen Statuscode im Bereich 5xx.

Aus dem Statuscodes-Wiki:

599 Netzwerkverbindungs-Timeout-Fehler (Unbekannt) Dieser Statuscode wird in keinem RFC angegeben, wird jedoch von HTTP-Proxys der Microsoft Corp. verwendet, um einem Client vor dem Proxy ein Netzwerkverbindungs-Timeout hinter dem Proxy zu signalisieren.

Ich verwende den benutzerdefinierten Statuscode 599 für ein Sitzungszeitlimit und überprüfe ihn dann in der AJAX-Antwort.

Dermot Doherty
quelle
3
Ein Zeitlimit für die Netzwerkverbindung unterscheidet sich stark von einem Zeitlimit für Sitzungen. Wenn Sie einen Code aus einer Microsoft-Erweiterung verwenden 440 Login Timeout (Microsoft)
möchten
Diese Wikipedia-Seite über 599 war falsch und hatte keine Zitate. Es wurde anscheinend immer gesagt, dass Microsoft-Proxys beim Netzwerk-Timeout 599 erhöhen, aber ich konnte auch keine Beweise dafür finden.
Gareth Davidson
11

Gemäß den Empfehlungen des HTTP - Statuscodes oberhalb von Bobo zur Verfügung gestellt:

440 Login Timeout (Microsoft)

    A Microsoft extension. Indicates that your session has expired.
Faisal Mq
quelle
Beachten
Sie
Ich mag diese Lösung für ASP.NET-Umgebungen.
TroySteven
8

Während Sie einen Link posten, habe ich in diesem Link diesen HTTP-Statuscode 440 gefunden . Sie können den 440 HTTP-Statuscode für abgelaufene Sitzungen verwenden.

440 Anmeldezeitlimit

 The client's session has expired and must log in again.

401 Nicht autorisiert können wir verwenden, wenn die Anmeldeinformationen des Benutzers falsch sind. oder im Header übergebenes Authentifizierungstoken ist ungültig.

403 Verboten können wir dies verwenden, wenn der Benutzer keine spezifische Berechtigung für die angeforderte Ressource hat.

Meiner Meinung nach sollten wir also 440 Login Timeout verwenden .

Vinay Pandya
quelle
2

Technisch gesehen ist die akzeptierte Antwort natürlich richtig: Wenn Sie bereits sicher sind, dass die Anforderung fehlschlagen wird, und Sie fragen, welchen Fehlercode Sie zurückgeben sollen, ist HTTP 401 "Nicht autorisiert (nicht authentifiziert)" die richtige. um eine erneute Authentifizierung zu veranlassen.

Aber fragen Sie sich zunächst: Sollten Sie die Anfrage nicht bestehen?

Bedenken Sie, dass der Benutzer möglicherweise einfach eine öffentliche Seite Ihrer Website besucht. In diesem Fall schlagen Sie sie mit einem "Unauthorized!" Nachricht, und sie müssen sich erneut authentifizieren, um eine Seite anzuzeigen, die sie normalerweise ohne Authentifizierung sehen könnten. Das ist nicht cool.

Mein Rat ist, die Tatsache zu ignorieren, dass das Sitzungstoken unbekannt ist, und einfach ein neues Sitzungstoken zu generieren und eine neue Sitzung dafür zu erstellen. Der Anfangszustand der Sitzung ist natürlich "noch nicht authentifiziert". Wenn der Benutzer also versucht, auf eine nicht öffentliche Seite zuzugreifen, wird die Seite dafür sorgen, dass er ein HTTP 401 "Nicht autorisiert (nicht authentifiziert)" erhält. "und muss sich authentifizieren. Wenn der Benutzer jedoch auf einer öffentlichen Seite landet, bemerkt er nichts anderes.

Mike Nakis
quelle
0

Ich würde eine 302-Umleitungsantwort verwenden, wobei ein "Location" -Header auf einen Ressourcenpfad wie "/ auth-required" verweist.

Der Client kann den Ressourcenpfad mit einem Anmelde- / Kennwortformular an ein Modal weiterleiten, ohne den Benutzer auf eine andere Seite zu übertragen.

Kiefer
quelle
-3

Für Nicht-Ajax-Anfragen verwende ich eine 302-Umleitung.

Für Ajax-Anfragen verwende ich 200 für bekannte Fehler. Auf diese Weise kann ich das Datenobjekt nutzen. Ich finde es einfacher, mit dem Datenobjekt zu arbeiten, als jqXHR nach Informationen zu durchsuchen. Und dann brauche ich keine Sorgen zu machen über das, was HTTP - Statuscode zu versuchen Wieder Zweck für meine Situation.

jQuery Beispiel:

$.ajax({
    //send data to server
})
.done(function(data, textStatus, jqXHR) {
    if (data.success) {
        //then process return data
    }
    else {
        //get error type or message from data object
        //could use custom error codes
    }
})
.fail(function(jqXHR, textStatus, errorThrown) {
    //handle unknown errors
});
Toxalot
quelle
6
Die Antwort nicht analysieren zu wollen, ist kein guter Grund, von der HTTP-Spezifikation abzuweichen, insbesondere wenn Sie nur JSON.parse (responseText) verwenden können.
David Nelson
Ich glaube nicht, dass die Verwendung eines 200-Antwortcodes in diesem Fall von der HTTP-Spezifikation abweicht, da die Anforderung auf der Transportebene technisch erfolgreich war. Für mich ähneln Sitzungszeitlimits Formularfehlern, bei denen ich eine benutzerfreundliche Fehlermeldung zurückgebe. Die Meinungsverschiedenheiten in den Antworten auf diese Frage zum Ausdruck zeigen deutlich , dass die HTTP - Spezifikation ist nicht eine Industrie akzeptierten Antwortcode für Session Timeouts bieten. Wie kann man von einer Spezifikation abweichen, die es nicht gibt?
Toxalot
-4

Code 408. "Timeout anfordern" scheint perfekt zu sein - RFC 2616 erklärt, dass dies bedeutet

Der Client hat innerhalb der Wartezeit des Servers keine Anforderung erstellt.

dh genau eine "Auszeit", genau wie Sie es benötigen!

Alex Martelli
quelle
4
Ah, aber sehen Sie sich den Rest der Definition an: "Der Client kann die Anforderung zu einem späteren Zeitpunkt ohne Änderungen wiederholen." "Ohne Änderungen" würde bedeuten, dass eine neue Sitzung einfach durch erneutes Laden / Aktualisieren der Anforderung erstellt werden könnte. In den meisten Fällen muss sich der Benutzer bei Verwendung der Authentifizierung zuerst erneut anmelden.
AJ.
@AJ, natürlich die wiederholte Anforderung kann in eine Authentifizierungsaufforderung ausführen (HTTP - Code 401) - sehe nichts in HTTP - Spezifikationen verbieten , dass können Sie auf etwas zeigen?
Alex Martelli
5
408 teilt dem Client mit, dass er einfach versuchen soll, die Anforderung unverändert erneut zu senden. Dies kann offensichtlich nicht funktionieren, wenn die Sitzung abgelaufen ist.
Tim Post
4
408 ist ein Anforderungszeitlimit, kein Sitzungszeitlimit. Das heißt, die Steckdose wurde eingerichtet, dauerte aber zu lange. Diese Seite macht einen guten Job, um es zu erklären: checkupdown.com/status/E408.html
Brad Cupit