HTTP Auth (wieder mal...)
x-herbert
- php
Hi,
wieder mal das Thema HTTP Authentifizierung....
vorweg: ich habe etliche Seiten zu dem Thema duchgesehen, aber nicht das passende gefunden....
Also: ich habe ein Verzeichnis per .htaccess geschützt (www.hier.de/geheim/) und möchte das das Verzeichnis bzw. Dateien in dem Verzeichnis direkt von einer per Session (PHP) geschützten Seite aufgerüfen werden kann (session.php).
Am einfachsten kann man natürlich das Verzeichnis "/geheim/" per Link
http://user:passwd@www.hier.de/geheim/ aufrufen oder z.B. per
header("Location: "http://user:passwd@www.hier.de/geheim/");
in einem Script.
Leider steht dann in der URL "user" und "passwd" :-(
Gibt es eine Möglichkeit die beiden Variablen dem Header auf eine "verdecktere" Art und Weise mit auf den Weg zu geben???
Gruss x-herbert
Hallo x-herbert,
header("Location: "http://user:passwd@www.hier.de/geheim/");
Dieses URL-Schema wird zwar von den meisten Browsern akzeptiert, ist jedoch offiziell nicht erlaubt.
Gibt es eine Möglichkeit die beiden Variablen dem Header auf eine "verdecktere" Art und Weise mit auf den Weg zu geben???
Nein.
Grüße,
Christian
@ Christian
Mir ging es um folgende Fragestellung:
wieso ist das Konstrukt
"user:pass@www.domain.de" vom Browser abhängig?? was macht den der Browser aus der URL, dass der Webserver was damit anfangen kann? Kann man diese "Umwandlung" nicht vorwegnehmen und direkt vom Script aus senden??
Gruss x-herbert
Hallo x-herbert,
@ Christian
Das ist hier nicht notwendig. Ich sehe schon, ob Du auf mich oder auf jemanden anderen antwortest. (</faq/#Q-03a>, http://aktuell.de.selfhtml.org/artikel/gedanken/foren-boards/)
wieso ist das Konstrukt
"user:pass@www.domain.de" vom Browser abhängig??
Eine HTTP-URL darf aus folgenden Komponenten bestehen:
http://host:port/path?search#anchor
Alles andere ist nicht erlaubt. Dass einige Browser es trotzdem akzeptieren, macht es trotzdem nicht richtig.
was macht den der Browser aus der URL, dass der Webserver was damit anfangen kann?
Nicht-standardkonforme Browser extrahieren Benutzernamen und Passwort und senden diese als HTTP-Authentication-Header mit.
Kann man diese "Umwandlung" nicht vorwegnehmen und direkt vom Script aus senden??
Nur wenn Dein Script sozusagen als "Proxy" fungiert und alle Requests selbst durchführt. z.B. so:
http://irgendwas/script.php?url=http://.../geschuetzt/xyz.gif
(wobei hier die /-Zeichen nach dem ?-Zeichen eigentlich auch kodiert werden müssten - bin nur zu faul nachzuschauen, wie)
Dann müsste Dein Script die HTTP-Requests selbst absetzen. Das wäre möglich, jedoch w+rde es die ganze Ausführung um einiges verlangsamen.
Grüße,
Christian
Das ist hier nicht notwendig. Ich sehe schon, ob Du auf mich oder auf jemanden anderen antwortest. (</faq/#Q-03a>, http://aktuell.de.selfhtml.org/artikel/gedanken/foren-boards/)
o.k. ...
Nur wenn Dein Script sozusagen als "Proxy" fungiert und alle Requests selbst durchführt. z.B. so:
http://irgendwas/script.php?url=http://.../geschuetzt/xyz.gif
(wobei hier die /-Zeichen nach dem ?-Zeichen eigentlich auch kodiert werden müssten - bin nur zu faul nachzuschauen, wie)Dann müsste Dein Script die HTTP-Requests selbst absetzen. Das wäre möglich, jedoch w+rde es die ganze Ausführung um einiges verlangsamen.
..hmmm... habe ich noch nicht ganz kapiert :(
Der Schutz des Verzeichnisses muss nicht "Echolon-Sicher" sein - sollte aber den "normalen-neugierigen-Besucher" ausschließen. Zur Zeit habe ich folgende "Konstruktion":
Wenn man statt der header...usw. eine "andere" Variante verwenden könnte, wäre das Problem erstmal gelöst - und die Sicherheit für mich o.k.
gruss x-herbert
Nachtrag:
wenn ich einmal in einem mit .htaccess geschützten Verzeichnis eingeloggt bin, kann ich doch ein zweites Browserfenster öffnen und es kommt keine Loginabfrage - logisch...
Was sendet mein Browser?? Aus dem Logging des Webservers war dieSche nicht erkennbar. Es bibt sicher Pogramme, die das mitschneiden können.
Kann man nicht einfach einen solchen GET-Aufruf "basteln"?
gruss x-herbert
Hallo x-herbert,
Kann man nicht einfach einen solchen GET-Aufruf "basteln"?
Wenn Du selbst Client spielst (was ich vorgeschlagen habe) - sicherlich. Es gibt dazu mehrere Header, Du solltest Dir mal den Standard für HTTP-Authentifizierung durchlesen: http://www.ietf.org/rfc/rfc2617.txt. (Warscheinlich reicht Dir Basic Authentication - Digest Authentication kannst Du überspringen) Wenn Du nur etwas an den Browser zurücksenden willst, um ihn zu veranlassen - nein, das geht nicht.
Grüße,
Christian
Hi Christian,
ich glaube, ich hatte einen Gedankenfehler mit dem Absetzen des "header":
Wenn ich das jetzt richtig verstanden habe, erzeugt der Befehl "header(...)" im PHP-Script einen Header, der zurück an den abfragenden Browser gesandt wird. Das nützt dann natürlich recht wenig, denn das Script müßte einen Client simulieren und eine GET abfrage an den Browser (mit dem geschützten verzeichniss) absetzten. Das wird sicher schwierig werden, da der Webserver auf diese Anfrage die Antwort "an das Script senden" müsste.
Eine Möglichkeit wäre ggf. mit "socket" zu arbeiten - ist bei meinem Provider nicht implementiert :(
So bleibt warscheinlich nur eine clientseitige Lösung - vielleicht mit Javascript oder einem kleinen Javaapplet...
Bitte um Berichtigung, wenn ich falsch liege!! & Danke für die Antworten
Gruss x-herbert
noch´n Nachtrag
habe dochnoh das gleiche Problem gefunden (ohne Lösung)
http://forum.de.selfhtml.org/archiv/2000_2/t13377.htm
Gruss x-herbert
Hallo x-herbert,
denn das Script müßte einen Client simulieren und eine GET abfrage an den Browser (mit dem geschützten verzeichniss) absetzten.
Wenn Du jetzt statt Browser Server meinst, dann ist es das, was ich Dir vorgeschlagen habe.
Das wird sicher schwierig werden, da der Webserver auf diese Anfrage die Antwort "an das Script senden" müsste.
Wo ist das Problem?
Eine Möglichkeit wäre ggf. mit "socket" zu arbeiten - ist bei meinem Provider nicht implementiert :(
socket vielleicht nicht, aber fsockopen wird von _jeder_ PHP-Version, die ich in letzter Zeit gesehen habe, unterstützt. Im PHP-Handbuch gibt's sogar einige Beispiele, wie man mit fsockopen Dateien von einem Server holt - die lassen sich sicherlich anpassen.
Grüße,
Christian
Hi Christian,
mit fsockopen funktioniert die Sache prinzipiell (hab´s ausprobiert...)
... leider werden die ganzen Linkbezüge der aufgerufenen Seite (im geschützten Verzeichnis) durcheinander gewürfelt, so dass Bilder nicht angezeigt werden und Links nicht stimmen (soweit auch logisch).
Da die Authentifizierung vom Script und nicht vom Browser erfolgte, werden alle weiteren Zugriffe auf Dateien innerhalb des geschützten Verzeichnisses mit der Auth-maske quitiert :(
... ist also noch nicht das gelbe vom Ei.
Zwei Fragen noch (vor der "Nachtruhe"...)
kann man die Authentifizierung per Coockie an den Browser senden?
welche Möglichkeiten gibt es noch ein Verzeichnis zu schützen (insbesondere bei Dateien wie JPG/PDF/ZIP u.ä.) mit PHP/Perl/Python
(habe mal die Sache über die htaccess per
Satisfy Any
Order Deny,Allow
Deny from all
Allow from .nolimits.de
versucht => funktionierte aber irgendwie "überhauptnicht")...
Gruss x-herbert
Hallo x-herbert,
... ist also noch nicht das gelbe vom Ei.
Es sei denn, Du tauscht alle Links dynamisch aus...
- kann man die Authentifizierung per Coockie an den Browser senden?
Nein. Wie stellst Du Dir das denn vor?
- welche Möglichkeiten gibt es noch ein Verzeichnis zu schützen (insbesondere bei Dateien wie JPG/PDF/ZIP u.ä.) mit PHP/Perl/Python
Ganz einfach: Stecke die Dateien in ein für den Webserver unzugänglichen Bereich (kann auch ein Deny From all sein) und schreibe ein Script, das sie nur bei korrekter Session + Benutzerkennung in der Session »durchschleift«. (fpassthru)
Grüße,
Christian
Moin Christian,
... ist also noch nicht das gelbe vom Ei.
Es sei denn, Du tauscht alle Links dynamisch aus...
phuu.. ist mir zu viel Arbeit ;-) => werd´s aber im Hinterkopf behalten..
- kann man die Authentifizierung per Coockie an den Browser senden?
Nein. Wie stellst Du Dir das denn vor?
»»
Ich denke schon: siehe http://fiatlux.zeitform.info/anleitungen/zugriffsbeschraenkung.html#mod_auth_cookie
Soweit ich das verstanden habe, sollte folgendes möglich sein: ich setze in meinem "Session-Script" einen Cookie (mit usr:pass) und leite dann an das geschützte Verzeichnis weiter => sofern der User keine Cookies aktzeptiert, muss er sich mit der Authentifizierungsmaske rumschlagen - wenn Cookies akteptiert werden, hat er "freie Fahrt" auf das Verzeichnis. Damit nicht alle User das gleiche "usr:pass" verwenden ("müssen") könnte man hier noch eine Variation einbauen und die Daten für den Login ("Session-Script") für die .htpassw verwenden oder schöner einen Zugriff über mod_auth_mysql... werde die Sache mal probieren => geht aber erst heute Nachmittag/Abend
- welche Möglichkeiten gibt es noch ein Verzeichnis zu schützen (insbesondere bei Dateien wie JPG/PDF/ZIP u.ä.) mit PHP/Perl/Python
Ganz einfach: Stecke die Dateien in ein für den Webserver unzugänglichen Bereich (kann auch ein Deny From all sein) und schreibe ein Script, das sie nur bei korrekter Session + Benutzerkennung in der Session »durchschleift«. (fpassthru)
»»
hmmm... der Schutz mit dem "Deny,Allow" hat irgendwie nicht so richtig funktioniert (vielleicht liegt es an der Apacheimplementierung - die ich nicht ändern kann..) Ich habe mir mal die Beispiele im PHPManual zu fpassthru angesehen - so richtig auf den Trichter bin ich für eine Lösung "meines" Problems nicht gekommen. Vielleicht hast Du noch ein, zwei Infos für mich, wie Du das meinst...
Gruss x-herbert
Hallo,
hmmm... der Schutz mit dem "Deny,Allow" hat irgendwie nicht so richtig funktioniert (vielleicht liegt es an der Apacheimplementierung - die ich nicht ändern kann..) Ich habe mir mal die Beispiele im PHPManual zu fpassthru angesehen - so richtig auf den Trichter bin ich für eine Lösung "meines" Problems nicht gekommen. Vielleicht hast Du noch ein, zwei Infos für mich, wie Du das meinst...
Naja, ein Beispiel:
So sieht es jetzt aus: (Vereinfacht)
Wurzelverzeichnis
|- index.php (mit Session »geschützt«)
|- script.php (mit Session »geschützt«)
- gesch\_verz/ (mit HTTP-Auth geschützt) |- gesch\_datei1.html |- gesch\_datei2.gif
- gesch_datei3.gif
So könnte es dann aussehen:
Wurzelverzeichnis
|- index.php (mit Session »geschützt«)
|- script.php (mit Session »geschützt«)
|- passthru.php (mit Session »geschützt«)
- gesch\_verz/ (komplett gesperrt) |- gesch\_datei1.html |- gesch\_datei2.gif
- gesch_datei3.gif
Du könntest dann Links wie
http://domain/passthru.php/gesch_datei1.html
zusammenbauen. Der Apache ruft automatisch passthru.php auf und Du kannst aus irgendeiner Servervariable (ich erinnere mich nicht mehr, welcher) den Namen der Datei herausholen und diese dann mit fpassthru durchreichen. (Vorher natürlich mit Sicherheitschecks, dass kein '..' im angegebenen Pfad vorhanden ist) PHP hat ja, da es direkt auf dem Webserver ausgeführt wird, Zugriff auf die Dateien in gesch_verz, der Apache wird über
Order Deny, Allow
Deny From all
dazu gebracht, nur noch "403 Forbidden" auszuspucken.
Wenn Du absolute Links in den Dateien verwendest, dann müsstest Du halt einmal in allen Dateien gesch_verz durch passthru.php ersetzen, aber sonst ist diese Lösung mit dem gerinsten Aufwand verbunden. (Wenn wir jetzt mal von allen »sauberen« Lösungen ausgehen, http://user:pass@host/path ist ja nicht »sauber«)
Grüße,
Christian
Hi Christian,
Danke für die ausführiche Erklärung!! => werde ich so ausprobieren!!
Gruss x-herbert
Hi,
Danke für die ausführiche Erklärung!! => werde ich so ausprobieren!!
Aber denke daran, die Dateinamen in der url zu überprüfen, sonst kann ein "lustiger" Besucher einen Dateinamen mit ../../qwer angeben, und damit alle Dateien öffnen auf die der Apache ein Recht hat. Das verfahren habe ich mal im Prinzip so vorgeschlagen, und das vergessen anzugeben. Zum Glück hat es Michael Schröpl sofort bemerkt ;-).
mfg Andres Freund
Moin,
mein "Weiterleitungsscript" wird nur bei einer vorhandenen und entsprechend gültigen Sessionvariablen (vom Login) ausgeführt
die Query´s sind nur für ein definiertes Verzeichnis erlaubt und für entsprechende Dateien (Extensions)
=> damit sollte die Sache erstmal relativ "sicher" sein
Gruss x-herbert
Hi Christian,
mit...
Wurzelverzeichnis
|- index.php (mit Session »geschützt«)
|- script.php (mit Session »geschützt«)
|- passthru.php (mit Session »geschützt«)
- gesch\_verz/ (komplett gesperrt) |- gesch\_datei1.html |- gesch\_datei2.gif
- gesch_datei3.gifDu könntest dann Links wie
http://domain/passthru.php/gesch_datei1.html
funktioniert es wunderbar!!! :-))
nochmals Danke für den Tipp!!!
Gruss x-herbert
Hallo,
Also: ich habe ein Verzeichnis per .htaccess geschützt (www.hier.de/geheim/) und möchte das das Verzeichnis bzw. Dateien in dem Verzeichnis direkt von einer per Session (PHP) geschützten Seite aufgerüfen werden kann (session.php).
Eine Session stellt keinen Schutz für eine Seite dar.
(Widerspruch bitte hier:_____________________________)
Sie sorgt für die einfache Wiedererkennung eines Surfers. Erst durch die verwendung weiterer, von der Session unabhängiger Erkennungsmerkmale, erhält man relative Sicherheit. Das kann ein zusätzlicher temporärer Cookie sein in Verbindung mit einem Mechanismus, der z.B. sofort bei Fehlerhafter Kombination von Sessionnummer und "Sicherheitscookie" die Session sperrt (zerstört). Dadurch erhält man, was die reine Kombination betrifft, praktisch unendliche Sicherheit. Leider gibts immer noch Lauscher auf den Leitungen. Das zwerstört diese wunderschöne Theorie wieder...
Nun zu Session und Auth:
Der Zugriffsschutz von .htaccess erstreckt sich nur auf den Weg über HTTP. Das bedeutet, dass nur bei einem Zugriff von Außen auf den Webserver geprüft word, ob Zugriffsrechte verlangt werden. Wenn man Host-intern, also vom Applikationserver auf das Filesystem zugreift, dann werden diese Rechte vom Apachen nicht geprüft. Das bedeutet, dass Du über ein entsprechendes Script auf jede "geschützte" Seite zugreifen kannst, auf die die Applikation (Apache, wwwrun) auf Fileserver-Ebene Zugriff hat.
Benutze einfach den Befehl readfile() oder passthru() oder so ähnlich. Ggf. musst Du noch einen passenden Header mit dem richtigen DocType vorausschicken, aber das müsstest Du hinbekommen.
Liebe Grüße aus http://www.braunschweig.de
Tom
Hallo Tom,
Eine Session stellt keinen Schutz für eine Seite dar.
Gleich zur Liste meiner Lieblingszitate aus dem SELFForum hinzugefügt. Diese Tatsache war nämlich für mich so offensichtlich, dass es mir nie in den Sinn gekommen wäre, sie zu erwähnen.
Danke,
Christian
Hallo Tom,
Eine Session stellt keinen Schutz für eine Seite dar.
Gleich zur Liste meiner Lieblingszitate aus dem SELFForum hinzugefügt. Diese Tatsache war nämlich für mich so offensichtlich, dass es mir nie in den Sinn gekommen wäre, sie zu erwähnen.
Hmmmm, so offensichtlich find ich das nicht. Wenn ich daten über eine session schütze, also zb über nen login system relevante daten in der session speichere wie kann dann jemand anders daran kommen ?
Die frage habe ich mir kürzlich auch gestellt, wie sicher sind session eigentlich?
Ich meine ich versuche nicht nen hochsicherheits bereich auf meiner seite zu erstellen, aber eigentlich will ich nicht das x-belibige "hacker" auf diese daten zugreifen kann...
also login per formular, daten check aus msqldb, wenn ok dann session_start().
dann kann man doch eigentlich _nur_ als eigeloggter user zb. im forum posten wenn ich das so will ?
wieder ein beispiel:
if ( $_GET["action"] && $_GET["action"] == "update_user" && $_POST["id"] == $_SESSION["id"]) { ... }
damit könnte nur der sein daten verändern der sie verändern soll oder ?
in dem fall seine eigenen daten ändern, in dem in einem hidden field die id übergeben wird...
Bin ich aufn falschen dampfer?
Mfg Analpha
Hallo!
also login per formular, daten check aus msqldb, wenn ok dann session_start().
dann kann man doch eigentlich _nur_ als eigeloggter user zb. im forum posten wenn ich das so will ?
Kommt drauf an wie DU das genau machst, wenn Du nur prüfst ob eien Session existiert könnte er die sich evtl auch in einem anderen Script auf Deinem Server besorgen, theoretisch.
wieder ein beispiel:
if ( $_GET["action"] && $_GET["action"] == "update_user" && $_POST["id"] == $_SESSION["id"]) { ... }
Das ist schön und gut, aber man kann nur aussagen machen wenn man komplette Scipte sieht, denn es gibt viele Progammierfehler, die man ausnutzen könnte, udm eien Session mit einer gültigen ID zu bekommen... das Thema ist schon oft hier diskutiert worden, suche mal nach "session login", oder "session sicherheit"...
damit könnte nur der sein daten verändern der sie verändern soll oder ?
in dem fall seine eigenen daten ändern, in dem in einem hidden field die id übergeben wird...
So wie das da oben aussieht könnte er einfach die ID von einem fremden Posting in seine eigene ändern und könnte es so editieren, aber wie gesagt, ich habe meine Kristallkugel zur Zeit leider verliehen ;-)
Grüße
Andreas
PS: Denke daran das man nicht unbedingt genau Deine HTML-Seite und Deinen Server braucht um den HTTP-Request abzuschicken!
Hallo!
Moin
Naja ich versuch mich mal genauer auszudrücken, da fängt langsam an der schuh zu drücken ;)
Ich stell mir das so vor.
Zuerst der login. Daten in ein forumular eingeben die mit den daten ausner MySQL db verglichen werden, wenn ok dann login.
Nun bekommt der Surfer ne session id ( id = id in der mysql db ), die ist unabhängig davon was der browser für ne session id vergibt.
Wenn er jetzt zb nen forums post machen will, überprüfe ich zuerst ob in der session eine gültige session id gespeichert ist ( also ob der user überhaupt in der DB existiert )
Da fängt es doch schon an oder ?
In den forums-formular gibt es ein hidden field, darüber wird die session ID verschickt. Auf der zu verarbeitenden seite überprüfe ich ob $_POST["sessionID"] gleich der $_SESSION["id"] ( wieder die ID des users aus der login db ) ist. wenn das nicht der fall ist - kein post.
Theorethisch - zumindest denke ich das - dürfte auch wirklich nur ein eigeloggter user nen post machen können, oder?
Er kann zwar ein externes formular machen, was die gleiche id hat wie die die er im quelltext lesen kann ( die er eigentlich nicht lesen kann, weil wenn er es lesen könnte bräuchte er sich die mühe nicht machen ) er wird aber niemals an die sessionID kommen die ich der session nach dem login verpasse, also die ID aus der db. oder?
PS: Denke daran das man nicht unbedingt genau Deine HTML-Seite und Deinen Server braucht um den HTTP-Request abzuschicken!
Jo das ist mir klar ;)
Mfg Analpha
Hallo Analpha,
Theorethisch - zumindest denke ich das - dürfte auch wirklich nur ein eigeloggter user nen post machen können, oder?
Natürlich. Aber Thomas (und mir) ging es um folgendes: Sessions dienen dazu, dass man Informationen über einen Besucher speichern kann und diese über mehrere Requests hinweg nutzen kann. Sessions können, wie in Deinem Fall _auch_ dazu benutzt werden, einen Login zu realisieren, aber auch für anderweitige Sachen, z.B. Usertracking. Sessions alleine bieten gar keine Sicherheit, jemand muss sich schon Gedanken über ein Sicherheitskonzept gemacht haben.
Grüße,
Christian
Hi Christian, Analpha und Andreas,
Natürlich. Aber Thomas (und mir) ging es um folgendes: Sessions dienen dazu, dass man Informationen über einen Besucher speichern kann und diese über mehrere Requests hinweg nutzen kann. Sessions können, wie in Deinem Fall _auch_ dazu benutzt werden, einen Login zu realisieren, aber auch für anderweitige Sachen, z.B. Usertracking. Sessions alleine bieten gar keine Sicherheit, jemand muss sich schon Gedanken über ein Sicherheitskonzept gemacht haben.
Genau das ist der entscheidende Punkt. Meiner Meinung nach darf die Session eben erst dann gestartet, reaktiviert oder abgewiesen werden, wenn die Authentifikation stattgefunden hat. Es gibt also nur für valide User eine Session, wenn sie bereits angemeldet sind. Aber auch das bedeutet nicht, dass eine Session dann die "Anmeldung weitertragen" kann, es sind _zwei_ Mechanismen die zur Sicherheit _getrennt_ laufen sollten. Gut, mann kann in der Session einen _Schlüssel_ auf den Auth-Datensatz in der DB parken, am besten mit einer zweiten _eindeutig_ erzeugten ID, aber mehr sollte man das ganze nicht verzahnen. Und: Es muss immer sichergestellt sein, dass bei Zweifeln eher abgebrochen wird, als auf Verdacht weiter zu machen.
Fabian
@ "die Antworter"
natürlich ist eine Session per se kein Schutz einer Seite - das Thema war auch nicht die grundlegende Fragestellung....
Mir ging es um folgende Fragestellung:
Gruss x-herbert
Hallo x-herbert,
- ==> Auf-/Abruf soll _OHNE_ nochmalige Authentifizierungsmaske bzw. Eingabe erfolgen
Wie gesagt - das geht nur mit der Methode
http://user:pass@host/path?search
Und auf diese kannst Du Dich nicht verlassen, weil sie nicht standardkonform ist.
Etwas anderes ist nicht möglich - Du kannst HTTP Authentication _nicht_ mit Session-Login verbinden.
Grüße,
Christian
Hallo!
Du(x-herbert) könntest Dir ne nette Sicherheitslücke einbauen indem Du ein Script außerhalb des per Basic-Auth geschützten Verzeichnisses legst, welches intern auf die gesuchten Daten zugreift und wie Thomas beschreiben hat weiterreicht. Wie gesagt sollte das genau überlegt sein, wenn Du das nicht vernünftig schützt kann jeder trotz .htaccess über diesen Umweg an die geschützten Daten kommen.
Direkt über HTTP ist es definitiv nicht möglich, zumindest für einen Teil der User.
Grüße
Andreas
Hallöle Andreas,
Du(x-herbert) könntest Dir ne nette Sicherheitslücke einbauen indem Du ein Script außerhalb des per Basic-Auth geschützten Verzeichnisses legst, welches intern auf die gesuchten Daten zugreift und wie Thomas beschreiben hat weiterreicht.
Ich habe mich da wohl etwas missverständlich ausgedrückt. Nicht "weiterreichen" sondern mit Hilfe einer DB und einer Bild-ID den Pfad und den Typ für das Bild bestimmen und dann ausliefern. Außerdem sollte das Script ja auch so intelligent geschrieben sein, das es vorher prüft, welcher User welche Datei überhgaupt haben darf. Dazu taugt dann auch wieder die DB.
Liebe Grüße aus http://www.braunschweig.de
Tom
o.k.
ich glaube, ich bin auf dem richtigen Dampfer...
Ich habe nun ein "Weiterreichungsscript" dessen Aufruf "geschützt" ist und das nur bestimmte Query´s annimmt
Danke nochmal für die Hilfe
x-herbert
Hallo Herbert,
das hatte ich Dir eigentlich auch beantwortet.
Leg das Verzeichnis ausserhalb der Document Root oder lass es mit .htaccess geschützt. Nun holst Du die Bilder nicht mehr mit einer Direktreferenz (<img src="bildname"...>) aus dem Verzeichnis, denn per HTTP kommst du ja nicht heran, sondern Du holst sie mit Hilfe eines PHP-Scriptes (<img src="getpic.php?ID=1234456" ...>) aus dem Verzeichnis. In diesem Script muss natürlich vorher die User-Identifikation mittels Sessionnummer und SessionPIN stattfinden. Dann kannst Du Dir aus der Datenbank den Dateinamen besorgen und das Bild mittels readfile() ausgeben. Vorher musst Du noch den Doc-Type-Header senden. ICh wiederhole mich aber...
Liebe Grüße aus http://www.braunschweig.de
Tom
Hallo zusammen,
...einen _Schlüssel_ auf den Auth-Datensatz in der DB parken, am besten mit einer zweiten _eindeutig_ erzeugten ID, aber mehr sollte man das ganze nicht verzahnen. Und: Es muss immer sichergestellt sein, dass bei Zweifeln eher abgebrochen wird, als auf Verdacht weiter zu machen.
das trifft so ungefähr die Problematik. Eine Sessionnummer gibt nur eine Positivaussage, wenn sie passt. Leider ist diese Aussage nicht umkehrbar, da HTTP kein verbindungsorientiertes Protokoll ist. Wenn die Sessionnummer die einzige Größe ist, über die ein User erkannt werden kann, dann stellt sie kaum einen Schutz dar. Der User könnte ja theoretisch beliebig oft wiederkommen und damit gültige Sessionnummern erraten. Da es keine Möglichkeit gibt, festzustellen, ob es der selbe User ist (wie gesagt, alles Theorie), aknn man ihn auch nicht aussperren. Da aufgrund der Positiverkennung auch nicht festgestellt werden kann, welche Sessionnummer attakiert wird, kan man diese auch nicht schützen.
Das ganze ändert sich, wenn man eine Authentifizierung mittels Datenbank und einem Schlüsselpaar (Loginname und Passwort sind da üblich) vorschaltet und dan auf ein anderes Schlüsselpaar (Sessionummer und SessionPIN, beides Cookies) umschaltet. Nun ist es plötzlich nicht mehr möglich, eine "erratene" Sessionnummer einfach zu benutzen, da auch der Key dazu passen muss. Dem Server ist jetzt in der Lage, die attakierte (zufällig erratene) Session sofort zu sperren (also nicht unbedingt zu vernichten). Leider verliert dann zwar auch der rechtmäßige Besitzer die Verbindung zu seinen Daten, aber der kann sich ja neu anmelden und die abgebrochene Session wiederaufnehmen. Das ist allemal billiger, als ein Loch auf dem Konto oder die Blamage, wenn die Liebesbriefe plötzlich veröffentlicht werden *gg*.
Ich hoffe, ich konnte die Problmatik nun noch mal etwas deutlicher machen.
Übrigens braucht man beim AUTH-Verfahren keinen zusätzlichen Cookie, da ja bereits ein Schlüsselpaar vorhanden ist, das jedes Mal geprüft werden kann (eigentlich muss!). Die Session besteht dann darin, aus einer Datei die daten wiederherszustellen und mit register_shutdown_function() beim Scriptstart ein shutdown_script anzumelden, dass am Ende oder bei Abbruch des Scriptes die Sessiondaten wieder in diese Datei hineinschreibt.
So einfach ist das.
Liebe Grüße aus http://www.braunschweig.de
Tom
Moin!
...einen _Schlüssel_ auf den Auth-Datensatz in der DB parken, am besten mit einer zweiten _eindeutig_ erzeugten ID, aber mehr sollte man das ganze nicht verzahnen. Und: Es muss immer sichergestellt sein, dass bei Zweifeln eher abgebrochen wird, als auf Verdacht weiter zu machen.
das trifft so ungefähr die Problematik. Eine Sessionnummer gibt nur eine Positivaussage, wenn sie passt. Leider ist diese Aussage nicht umkehrbar, da HTTP kein verbindungsorientiertes Protokoll ist. Wenn die Sessionnummer die einzige Größe ist, über die ein User erkannt werden kann, dann stellt sie kaum einen Schutz dar.
Hier möchte ich widersprechen. Eine Session schützt genauso gut (oder schlecht) wie eine Username/Passwort-Authentifizierung.
Der User könnte ja theoretisch beliebig oft wiederkommen und damit gültige Sessionnummern erraten. Da es keine Möglichkeit gibt, festzustellen, ob es der selbe User ist (wie gesagt, alles Theorie), aknn man ihn auch nicht aussperren. Da aufgrund der Positiverkennung auch nicht festgestellt werden kann, welche Sessionnummer attakiert wird, kan man diese auch nicht schützen.
Dasselbe Argument kann man für Username/Passwort-Authentifizierung anbringen. Auch da kann der Angreifer beliebig oft wiederkommen und ausprobieren. Nur hat er da noch den kleinen Vorteil, dass er den menschlichen Faktor einrechnen kann - wenn die User sich ihr Passwort frei wählen können, wird es mindestens einen User geben, der für Wörterbuchattacken anfällig ist - und BUMM.
Das ganze ändert sich, wenn man eine Authentifizierung mittels Datenbank und einem Schlüsselpaar (Loginname und Passwort sind da üblich) vorschaltet und dan auf ein anderes Schlüsselpaar (Sessionummer und SessionPIN, beides Cookies) umschaltet. Nun ist es plötzlich nicht mehr möglich, eine "erratene" Sessionnummer einfach zu benutzen, da auch der Key dazu passen muss.
Das ändert nichts grundsätzlich, es vergrößert nur den Aufwand.
Ich will das mal genauer ausführen:
Um in HTTP einen User wiederzuerkennen, muss dieser bei jedem Request ein eindeutiges Identifikationsmerkmal senden. _Alles_, was der berechtigte Benutzer sendet, kann ein Angreifer auch senden. Und alles kann durch Ausprobieren angegriffen werden.
Um den Benutzer also zu authentifizieren, ist entweder eine Username/Passwort-Kombination notwendig, oder ersatzweise eine gültige Session-ID. Die üblichen Session-Login-Mechanismen geben jedem Benutzer sofort eine Session-ID, und erst wenn der Benutzer innerhalb dieser Session einen gültigen Usernamen und Passwort gesendet hat, erlaubt die Session den Zugang zu geschützten Bereichen. Die Session-ID ist also zum Ersatz-Schlüssel geworden.
Du willst das jetzt angreifen. Dazu gibt es zwei Methoden: Entweder greifst du Username/Passwort an und errätst eine korrekte Kombination, oder du greifst die Session-ID an und errätst eine gültige Session.
Wie wahrscheinlich ist aber, dass dir eines von beiden gelingt? Beim Passwort-Angriff hast du zumindest theoretisch einen beliebig hohen Aufwand, sofern der Angreifer keinerlei Informationen hat. Sobald er einen Usernamen hat, ist eine Komponente schon mal geklärt, und mit Glück ist ein kurzes Passwort schnell geraten oder eine Wörterbuchattacke möglich.
Beim Raten der Session-ID hingegen gibt es nur endlich viele Kombinationen. Die PHP-SessIDs sind 128 Bit lange Zahlen, ausgedrückt als 32 Zeichen lange Hex-Zahl. 128 Bit ermöglichen 2^128 Kombinationen, oder etwa 3,4e+38.
Wieviele Versuche pro Sekunde soll ein Angreifer schaffen? Eine Milliarde? Das wären 1e+9 Versuche pro Sekunde, und es würde immer noch 3,4e+29 Sekunden dauern, bis alle Kombinationen ausprobiert sind. Durchschnittlich muß man nur die Hälfte aller Kombinationen ausprobieren, um eine einzig gültige Kombination rauszufinden - wenn mehrere Benutzer gleichzeitig aktiv sind, braucht man nicht mehr die Hälfte, sondern sogar noch einen kleineren Teil. Die 3,4e+38 Möglichkeiten könnten schön symmetrisch unterteilt sein. Wieviele Besucher sollen gleichzeitig aktiv sein? Eine Million? Ok, dann kriegt man nach 1/1.000.001stel Kombinationen die richtige raus (und nicht nach 1/2). Bleiben 3,4e+23 Sekunden, die ein Angriff dauert. Oder in Jahren: 10781329274479959,4114662607813293
Glaubst du nicht auch, dass dieser Angriff reichlich uninteressant ist. Natürlich kann man beim ersten Versuch Glück haben, aber systematisch kann man kaum angreifen.
Gucken wir noch, was man bei Username/Passwort an Sicherheit hat: Ein Username soll 10 Zeichen lang sein, ein Passwort ebenfalls. Erlaubt sind grob geschätzt 100 verschiedene Zeichen. Dann gibt es 100^10 verschiedene Usernamen und 100^10 verschiedenen Passwörter - insgesamt 1e+40 Kombinationsmöglichkeiten. Diese werden allerdings dahingehens eingeschränkt, dass nicht alle kombinierbaren Usernamen auch wirklich benutzt werden. Ich würde vermuten, dass erstens nur 62 Zeichen (Klein-/Grossbuchstaben, Zahlen) verwendet werden, und außerdem die Auswahl deswegen stark eingeschränkt ist, weil beschreibende Namen und keine kryptischen Passwörter gewählt werden. Also statt 1e+20 Usernamen gibt es nur 8e+17 Usernamen, und von denen dürften nicht mehr als 1% wirklich verwendet werden - also 8e+15 Stück. Macht zusammen 8e+35 Kombinationen - und das liegt absolut im Bereich der Möglichkeiten, wie sie Sessions auch bieten - zuzüglich dem menschlichen Faktor!
In Wirklichkeit ist also nicht die Session-ID das Problem, sondern Username/Passwort. Nur bei sehr günstigen Voraussetzungen (im Sinne der Sicherheit) ist die Angreifbarkeit ähnlich schlecht. Wenn hingegen nur kurze Usernamen und Passwörter und nur ein eingeschränkter Zeichenvorrat verwendet werden, dann sinkt die Sicherheit des Username/Passwort-Systems ganz rapide.
Sicherheit ist relativ. Ein System ist dann ausreichend sicher, wenn der Aufwand, die Sperren zu überwinden, teurer ist als der durch den Einbruch zu erwartende Gewinn. Außerdem gibt es absolute Sicherheit nicht - ein System wäre dann absolut sicher, wenn niemand rein kommt - auch keine berechtigten Benutzer. Denn ein Angreifer kann es immer irgendwie schaffen, sich als berechtigter Benutzer auszugeben. Selbst DNS-Kontrollen können garantiert umgangen werden - siehe den Film GATACA. :)
- Sven Rautenberg
Moin!
Wieviele Versuche pro Sekunde soll ein Angreifer schaffen? Eine Milliarde?
Zu bedenken ist: Welche Datenmenge kommt da auf den Webserver zu?
Einen HTTP-Header kann man relativ klein machen. Wichtig sind zwei Zeilen: GET und Host.
Host sei 30 Zeichen lang, GET sei 40 Zeichen lang - die Session-ID muss auch noch irgendwie mit - weitere 32 Zeichen. Zusammen grob 100 Zeichen.
Außerdem muß das ganze in ein TCP/IP-Paket, welches seinerseits noch 40 Byte hinzufügt.
Es prasseln also eine Milliarde TCP/IP-Pakete in der Größe von 140 Byte auf den Server ein. Das ist eine Datenrate von 1,4e+15 Bits pro Sekunde - oder auch 1,4 Petabit/s. Ja, ein Petabit sind 1000 Terabit oder eine Million Gigabit.
Wie wahrscheinlich ist das?
- Sven Rautenberg
Hallo!
Naja ich versuch mich mal genauer auszudrücken, da fängt langsam an der schuh zu drücken ;)
Wie gesagt, ohne genauen Code kann man da nicht all zu viel drüber sagen. Sachen die für den einen selbstverständlich sind, sind es für den anderen noch lange nicht!
Zuerst der login. Daten in ein forumular eingeben die mit den daten ausner MySQL db verglichen werden, wenn ok dann login.
Theoretisch OK.
Nun bekommt der Surfer ne session id ( id = id in der mysql db ), die ist unabhängig davon was der browser für ne session id vergibt.
seit wann vergibt ein Browser Session-IDs? Die SessionID gibt der Server dem Browser, ist also identisch mit der in der DB wenn ich das jetzt richtig verstanden habe.
Wenn er jetzt zb nen forums post machen will, überprüfe ich zuerst ob in der session eine gültige session id gespeichert ist ( also ob der user überhaupt in der DB existiert )
Ich blicke noch nicht ganz da durch was genau Du jetzt alles als SessionID bezeichnest, wo Du was speicherst.
In den forums-formular gibt es ein hidden field, darüber wird die session ID verschickt. Auf der zu verarbeitenden seite überprüfe ich ob $_POST["sessionID"] gleich der $_SESSION["id"] ( wieder die ID des users aus der login db ) ist. wenn das nicht der fall ist - kein post.
Es kommt drauf an was Du danach mit den Informationen genau machst! Wenn Du erst eine Prüfung machst ob die IDs übereinstimmen, und dannach, wenn erstere prüfung erfolgreich war, direkt das machst was der User will(Post abschicken/editieren...), dann könnte es Probleme geben. Du hast so sichergestellt, das es ein user aus der DB ist, also kann jeder User aus der DB Posten. Das wäre OK. Wenn Du jetzt z.B. ein Posting editieren willst, prüfst das genau wie oben und wenn die Prüfung erfolgreich war hast Du noch eine Posting-ID übermittelt und editierst das dann direkt, hast Du ein Problem, das jeder User jedes Posting editieren kann wenn er an den Parametern spielt. Du brauchst also noch vor dem editieren eine weitere Prüfung ob der User mit besagter UserID auch befugt ist dieses posting zu editieren, indem Du in der DB nachguckst ob Die Autor-ID mit der ID in der Session übereinstimmt.
Denn wenn Du die Parameter editPost.php?userID=123&postID=312 verwendest, könnte ich den Request einfach so abändern, dass ich userID in meine gültige ID ändere und schon darf ich das machen.
Aber vielleicht war Dir das auch klar, kann nur solche Sachen konstruieren ohne genauen Code der Dir Kopfschmerzen bereitet.
Theorethisch - zumindest denke ich das - dürfte auch wirklich nur ein eigeloggter user nen post machen können, oder?
ich denke schon. Schwieriger wird es wenn Du user-individuelle Aktionen wie editieren o.ä. ermöglichen willst.
Er kann zwar ein externes formular machen, was die gleiche id hat wie die die er im quelltext lesen kann ( die er eigentlich nicht lesen kann, weil wenn er es lesen könnte bräuchte er sich die mühe nicht machen ) er wird aber niemals an die sessionID kommen die ich der session nach dem login verpasse, also die ID aus der db. oder?
Die Frage ist ob er das braucht, ich denke posten kann er nicht ohne eingeloggt zu sein, aber auch das nur unter vorbehalt.
Grüße
Andreas
PS: in Zusammenhang mit PHP ist SessionID für mich der md5-String den PHP zufällig standardmäßig als $PHPSESSID vergibt.
Moin,
ich komme wphl nicht umhin code zu posten, das werde ich aber erst machen wenn ich fertig bin :).
Mal sehen
So long
Analpha