Session Management


(Session: Folge von Interaktionen eines Benutzers mit einer Webseite)


1. Notwendigkeit

Wenn ein Besucher eine Page im Web besucht, wird kurzzeitig eine Verbindung zwischen dem Besucher (client) und der Website (server) aufgebaut. Dies geschieht mittels eines Requests durch den Client, auf das der Server Informationen sendet. Das benutzte Protokoll, http, ist in der Version 1.0 verbindungslos , d.h. Server und Client nehmen dabei nie einen besonderen Zustand ein, es werden nur Kommandos und Antworten darauf gesendet.


Client: GET /index.html HTTP/1.0
If-Modified-Since: Fri, 18 Jan 2002 00:00:00
<ctrl>

Server: HTTP/1.0 200 Document follows
Date: Fri, 18 Jan 2002 14:02:23 GMT+200
Server: Apache/1.3.9 (Unix)
Last-Modified: Wed, 16 Jan 2002 13:12:28 GMT+200
Content-Length: 141
Content-Type: text/html

(content)

Dieser verbindungslose Ablauf ist zwar flexibel, störsicher und einfach, allerdings hat er auch einen gravierenden Nachteil. Sobald man sich mit dynamischer Webseitengestaltung beschäftigt, erkennt man das Bedürfnis, Benutzer zu identifizieren, sei es, um ihr Verhalten auf der Website zu studieren, bestimmte Personalisierungen vorzunehmen, oder sie als priviligierte Benutzer zu kennzeichnen (Authentifizierung).

Komplexere Anwendungen wie z.B. ein Webshop wären überhaupt nicht realisierbar, da ja jederzeit über einen Warenkorb des Besuchers "Buch geführt" werden muss, und wie wäre das möglich, wenn bei einem erneuten Request seitens des Clients keinerlei Informationen über den bisherigen Zustand vorhanden wären. Für statische, also unveränderliche Webseiten, wird in der Regel kein Sessionmanagement benötigt, hier reicht Http vollkommen aus.

Für das Sessionmanagement müssen also Informationen auf dem Client gespeichert werden, die beim nächsten Aufruf der Website wieder zur Verfügung stehen. Der Client selber kann nicht genügend Informationen für eine Wiedererkennung zur Verfügung stellen. Browsername, Betriebssystem und -Version reichen dafür nicht aus, und selbst die IP ist nicht eindeutig, da u.a. Proxies wie im Wohnheim HMS dafür sorgen, dass alle Benutzer nach außen die gleiche IP haben.

2. Techniken

Wie realisiert man nun, dass ein Benutzer während einer gesamten Session wiedererkannt wird?

2.1. Clientseitige Techniken

Im Gegensatz zu den serverseitigen Techniken, die allerdings aus oben genannten Gründen auch auf die Unterstützung der Clients angewiesen sind, wird hier der Server kaum belastet. Dadurch, dass allerdings alle Informationen auf dem Client gespeichert werden, ergeben sich jedoch vielfältige Angriffsmöglichkeiten. Außerdem können keine komplexen Informationen gespeichert werden. Folgende 3 Möglichkeiten gibt es:

2.1.1. Speicherung des Status in versteckten Feldern (hidden fields)

Der einfachste Weg, wenn auch nur eingeschränkt nutzbar, ist über versteckte Felder. Dabei werden einem Formular unsichtbare Informationen beigefügt, die dann mit abgeschickt werden. Sofort wird klar, dass dies nur möglich ist, wenn man sich von Formular zu Formular fortbewegt. Natürlich werden die Informationen sichtbar, wenn man sich den Quelltext der HTML-Seite anschaut.

<?php
if (!sessionid) {
mt_srand((double) microtime()*99999); // Zufallszahleneditorinit
$sessionid = md5(str_replace(".","",$REMOTE_ADDR) +
mt_rand(100000,999999)+time());
}

echo <<FORM // Ausgabe bis FORM
<form action="$PHP_SELF" method="post">
<input type hidden value="$session" name="session" />
Session ID: $session<p />
<input type submit value="weiter" />
</form>
<a href="$PHP_SELF">Neustart</a>
FORM;
?>


2.1.2. Speicherung des Status in der URI

Die URI (uniform resource indentificator) ist die erweiterte Form der URL; während diese nur den Link auf eine Webseite angibt, enthält die URI u.U. weitere Informationen.

http://www.amazon.de/exec/obidos/tg/browse/-/301128/028-1093462-2650149

Auch dieser Weg, ebenso wie 2.1.1, wird von allen Browsern unterstützt, ist aber schwieriger zu implementieren. Mann muss ja jeden Link in einem Dokument mit zusätzlichen Informationen versehen, die für jeden Benutzer einzigartig sind. Wenn man jedoch eh mit dynamischen Seiten arbeitet, ist dieser Weg auch ohne zu großen Aufwand realisierbar, ansonsten muss man die Html-Seiten vor der Anzeige parsen. Die Informationen, sofern nicht verschlüsselt, sind jedoch auch offen, und sehr leicht modifizierbar.

2.1.3 Nutzung von Cookies

Die dritte und wohl am universellsten nutzbare Methode sind wohl Cookies. Cookies (dt. Kekse) wurden erstmals von Netscape implementiert, um die Unzulänglichkeiten von Http zu beheben. Sie erlauben es auf einfache Weise, Informationen auf dem Client zwischenzuspeichern und eignen sich dadurch natürlich ideal für das Session-Management.

Cookies sind ein grundsätzlicher Mechanismus, den serverseitige Verbindungen (z.B. CGI-Skripte) nutzen können, um clientseitig Informationen zu speichern und wieder zu lesen. Dabei sendet der Server innerhalb eines Replies ein zusätzliches Informationsstück. Kann der Client mit Cookies umgehen, und sind diese nicht abgeschaltet, so werden dieses Textstück und weitere URL-Informationen vom Client abgespeichert. Bei jeder weiteren Anfrage an diese Domain (und nur diese!) werden nun vom Client die Textinformationen wieder zurückgesendet, und stehen dem verarbeitenden Script zur Verfügung. Somit ist klar, dass nicht der Server diese Informationen ausliest, sondern der Client sie sendet.

Der Cookie sieht im Html-Header folgendermaßen aus:

Set-Cookie: NAME=VALUE; expires=DATE; path=PATH; domain = DOMAIN_NAME; secure

Die eigentlichen Informationen werden durch Name=Value gesetzt, wobei es durchaus mehrere Wertepaare geben kann, die dann mit einem Semikolon getrennt werden.

In einem Cookie lassen sich, je nach Browser, ca. 4 Kbyte Informationen, 20 Cookies pro Domaion und 300 Cookies insgesamt speichern . Ausserdem haben sie eine bestimmte Lebenszeit. Mit expires kann diese gesteuert werden. Fehlt expires, erlischt der Cookie nach dem Schliessen des Browsers. Wird das angegebene Datum überschritten, sollte der Cookie vom Browser gelöscht werden, er wird auf jeden Fall nicht mehr gesendet. Damit lassen sich also auch Sessions über eine lange Zeit aufrechterhalten


Wird secure angegeben, so wird der Cookie nur gesendet, wenn eine sichere Verbindung (https) besteht.



Testen auf Cookies

Kommt ein User neu auf unsere Seite, wird eine neue Session gestartet, und normalerweise ein Cookie gesetzt. Sollte der Browser jedoch den Cookie verweigern, werden wir nicht davon unterrichtet, die Verbindung ist ja nach Request/Reply abgebrochen. Daher ist es manchmal notwendig zu testen, ob der Client Cookies akzeptiert, und im Zweifelsfall auf Url-Encoding umzusteigen, anderenfalls wird der User sich wundern, wieso er keinerlei Vorzüge des Sessionmanagements genießen kann.
Zum Testen wird nach dem setzen des Cookies auf eine weitere Seite weitergeleitet, die nur testen soll, ob der Cookie nun zurueckgesendet wird.


2.2. Serverseitige Techniken

Der letzte Punkt spricht ein wichtiges Thema an. Bei Html werden Informationen im Klartext übertragen. Wenn ich z.B. Username/Passwort während einer Session in der URL mitführe, dann ist es für jeden halbwegs versierten Sniffer möglich, sie zu ergattern. Dies, und die Möglichkeit, beliebige Informationen abzuspeichern, führt zur Verwendung von serverseitigen Methoden. Bei diesen wird jedem Benutzer eine eindeutige User/Sessionid zugeordnet. Diese könnte z.B. aus der Systemzeit, der Userip, und einer grossen Zufallszahl bestehen, welche zusätzlich noch verschlüsselt werden kann (z.B. md5) . Diese Userid wird mittels der clientseitigen Techniken während einer Session weitergereicht, alle weiteren Informationen werden auf dem Server z.B. in einer Datenbank gespeichert (MySQL), für die die SessionID Primärschlüssel ist. Alle komplexeren Webanwendungen basieren im Prinzip auf diesem Schema.





3. Weitere Aspekte des Sessionmanagements

3.1. Zeitfaktor

Eine Session sollte natürlich nicht unbegrenzt andauern, die Gründe dafür sind vielfältig und besonders gravierend, wenn es sich um eine authentifizierte Session handelt. Ein Beispiel. Cookies wurden deaktiviert, die Sessionid wurde in der URI übermittelt. Diese wird in der Browserhistory gespeichert. Wir verlassen den Computer, ein Kollege loggt sich ein, ruft die URI/URL aus der History auf. Schon kann er sich auf dieser Webseite als sein Vorgänger ausgeben, und alle diesem zugestandenen Privilegien nutzen. Andere Szenarien sind ebenfalls denkbar. Deshalb sollte man Sessions immer zeitlich begrenzen, d.h. man führt einen Zeitstempel zu jedem User, der die letzte Aktivität speichert. Sollte eine gewisse Zeitspanne in Inaktivität vergehen, dann wird die Session automatisch beendet.

3.2. Ip-check

Da theoretisch auch Sessionid's abgefangen werden können, kann zusätzlich noch die IP gespeichert und abgefragt werden. Dies ist allerdings schon sehr paranoid, Sicherheitsbedürftige Verbindungen sollten eh immer über https aufgebaut werden.

Anhang

Cookies und Sicherheitsaspekte
So schön Cookies auch sind, sie können jedoch auch missbraucht werden. Wenn man einmal seine Cookies durchforstet, so wird man sicherlich auf Cookies mit dem Namen doubleclick stossen:

id
8000000b2f5e9c1
doubleclick.net/
0
406055296
31593874
4251021792
29428673
*

Grund dafür: Doubleclick erstellt Userprofile, und arbeitet mit diversen Unternehmen zusammen. Diese leiten den User unbemerkt auf die doubleclick-Homepage, dort wird der User anhand des Cookies wiedererkannt, seine Besuche registriert, und somit ein genaues Userprofil erstellt, was den Partnern dann zur Verfügung gestellt wird. Dadurch kann dann z.B. gezielt Werbung geschaltet werden, usw.

Software

Für den einfachen Umgang mit Sessions bietet sich entweder das CGI-Modul von Perl oder PHP4 an,
dieses besitzt ein vollimplementiertes Sessionmanagement. Mehr dazu im Seminar PHP.

Literatur

PHP4 - Grundlagen und Profiwissen, Jörg Krause, Hanser Verlag, 2. überarbeitete Auflage

Links

Vortragshilfe
Word-Dokument