Zugriff auf bestimmte Dateien nur bestimmten Usern erlauben
Michael27
- programmiertechnik
Hallöchen,
ich speichere auf meinem Server Rechnungen im pdf-Format. Diese sollen Kunden später in Ihrem Account (solange sie eingeloggt sind) herunterladen können.
Andere Kunden (also mit anderer User_id) sollen ebenfalls nur ihre eigenen und keine fremden Rechnungen herunterladen dürfen.
Frage: Wie kann ich das realisierien, ohne für jeden User den Dateinamen mit kryptischen Zeichen zu versehen (damit andere User den Dateinamen nicht "erraten" können)?
Vielen Dank im Voraus
Hello,
ich speichere auf meinem Server Rechnungen im pdf-Format. Diese sollen Kunden später in Ihrem Account (solange sie eingeloggt sind) herunterladen können.
Andere Kunden (also mit anderer User_id) sollen ebenfalls nur ihre eigenen und keine fremden Rechnungen herunterladen dürfen.
Frage: Wie kann ich das realisierien, ohne für jeden User den Dateinamen mit kryptischen Zeichen zu versehen (damit andere User den Dateinamen nicht "erraten" können)?
Da gibt es unterschiedliche Vorgehensweisen.
Ich setze jetzt mal voraus, dass der Zugriff per HTTP oder HTTPS stattfindet.
Dann kann man die Files in einzelne Verzeichnisse sortieren und den Usern nur nach erfolgreicher Authentifikation Zugriff darauf gewähren. Das geht im Direktzugriff bei Apacheservern mittels "Basic Auth" oder "Digest Auth"
http://httpd.apache.org/docs/current/howto/auth.html
Wenn Du nicht auseinandersortieren willst, dann kannst Du auch über eine <Files>-Direktive oder <FilesMatch>-Diektive die Rechte für einzelne Files festlegen.
http://httpd.apache.org/docs/current/mod/core.html#files
http://httpd.apache.org/docs/current/mod/core.html#filesmatch
Alternativ kannst Du den Zugriff auch über Scripte regeln, also die Files nicht mehr direkt über HTTP/s ausliefern, sondern indirekt über ein Script, das vorher die Authentifizierung prüft.
Das gewählte Verfahren hängt unter anderem auch davon ab, ob Cookies benutzt werden dürfen, oder nur die Standardauthentifizierungen des Webservers.
Liebe Grüße aus dem schönen Oberharz
Tom vom Berg
Hallo,
Frage: Wie kann ich das realisierien, ohne für jeden User den Dateinamen mit kryptischen Zeichen zu versehen (damit andere User den Dateinamen nicht "erraten" können)?
"security by obscurity" wäre sowieso eine ganz schlechte Idee.
Im Prinzip kann man es so angehen:
* Alle in Frage kommenden Dateien liegen in einem Verzeichnis, auf das kein direkter Zugriff über
HTTP möglich ist (außerhalb Document Root, oder durch .htaccess gesperrt).
* Du hast sowieso schon ein Login, also ist z.B. die Kundennummer des aktuell anfragenden Besuchers
bekannt. Ein Script (PHP, Perl oder ähnlich) bietet dem Besucher nun *nur* die Dateien zum
Download an, die für ihn bestimmt sind (Info im Dateinamen, in einer DB oder einer separaten
Datei), und reicht sie einfach durch.
Mit welcher Scriptsprache möchtest du es realisieren? PHP dürfte die populärste sein.
So long,
Martin
Hallo,
da war ich wohl zu langsam ;-)
Viele Grüße Novi
Danke für die ganzen Antworten bisher.
Ich benutze in der Tat php und weiß über die UserId, ob ein Benutzer gerade
authorisiert ist oder nicht.
Die pdf-Rechnungen kann ich problemlos in einem öffentlich nicht zugänglichen Ordner speichern. Wie soll ich allerdings das pdf dann konkret "durchreichen" wie du meintest?
Hallo,
Frage: Wie kann ich das realisierien, ohne für jeden User den Dateinamen mit kryptischen Zeichen zu versehen (damit andere User den Dateinamen nicht "erraten" können)?
"security by obscurity" wäre sowieso eine ganz schlechte Idee.
Im Prinzip kann man es so angehen:
* Alle in Frage kommenden Dateien liegen in einem Verzeichnis, auf das kein direkter Zugriff über
HTTP möglich ist (außerhalb Document Root, oder durch .htaccess gesperrt).
* Du hast sowieso schon ein Login, also ist z.B. die Kundennummer des aktuell anfragenden Besuchers
bekannt. Ein Script (PHP, Perl oder ähnlich) bietet dem Besucher nun *nur* die Dateien zum
Download an, die für ihn bestimmt sind (Info im Dateinamen, in einer DB oder einer separaten
Datei), und reicht sie einfach durch.
Mit welcher Scriptsprache möchtest du es realisieren? PHP dürfte die populärste sein.So long,
Martin
Ich zitiere einfach mal von php.net:
"<?php
// Wir werden eine PDF Datei ausgeben
header('Content-type: application/pdf');
// Es wird downloaded.pdf benannt
header('Content-Disposition: attachment; filename="downloaded.pdf"');
// Die originale PDF Datei heißt original.pdf
readfile('original.pdf');
?>" (http://de.php.net/manual/de/function.header.php)
Ich denke, dass dir das schon weiterhelfen sollte.
Viele Grüße Novi
Hallo,
readfile('original.pdf');
wobei hier noch anzumerken wäre, dass PHP selbstverständlich auch auf Dateien und Verzeichnisse zugreifen kann, die nicht für HTTP gesperrt sind - hier findet ja kein HTTP-Zugriff statt.
Ciao,
Martin
wobei hier noch anzumerken wäre, dass PHP selbstverständlich auch auf Dateien und Verzeichnisse zugreifen kann, die nicht für HTTP gesperrt sind - hier findet ja kein HTTP-Zugriff statt.
Aber nur wenn die Rechte auf dem Webserver passen ;)
Sauber, vielen Dank für die vielen Antworten.
Ich werde das jetzt so probieren: pdfs in einem Ordner speichern, der nicht im DocumentRoot liegt. Dann werde ich es mit readfile('original.pdf');
probieren auszugeben, so wie Novi in seinem Post geschrieben hat.
Ich geb später mal Rückmeldung :)
Hello,
Sauber, vielen Dank für die vielen Antworten.
Ich werde das jetzt so probieren: pdfs in einem Ordner speichern, der nicht im DocumentRoot liegt. Dann werde ich es mit
readfile('original.pdf');
probieren auszugeben, so wie Novi in seinem Post geschrieben hat.
Das ist sicherlich die vernünftigste Lösung, hat nur einen Nachteil:
Die blockweise (chunked) Ausgabe wird dann nicht mehr unterstützt und die ist gerade bei PDF's nicht unwichtig, weil es meistens Megabyteklötze sind.
Man kann das aber auch in PHP-Scripten nachbilden. Dies fängt aber schon bei der Auswertung der Request-Header an.
Liebe Grüße aus dem schönen Oberharz
Tom vom Berg
Hello,
Danke für die ganzen Antworten bisher.
Ich benutze in der Tat php und weiß über die UserId, ob ein Benutzer gerade
authorisiert ist oder nicht.
Die pdf-Rechnungen kann ich problemlos in einem öffentlich nicht zugänglichen Ordner speichern. Wie soll ich allerdings das pdf dann konkret "durchreichen" wie du meintest?
Da schaust Du einfach mal ins PHP-Handbuch unter readfile().
Dort gibt es ein Beispiel
http://de.php.net/manual/en/function.readfile.php
Und vergiss nicht, auch das hiesige Archiv danach zu befragen. Es gibt nämlich noch etliche Sonderfälle und Zusatzbemerkungen dazu. "Download" wäre ein Suchbegriff...
Liebe Grüße aus dem schönen Oberharz
Tom vom Berg
Hallo,
ich würde die Rechnungen alle in einem Ordner speichern, auf den niemand über das HTTP-Protokoll zugreifen kann. Dies lässt sich zum Beispiel leicht über eine .htaccess Datei mit folgendem Inhalt lösen: Deny from all
.
Dies bedeutet aber nicht, dass Scripte/Programme auf deinem Server nicht darauf zugreifen können. Also kannst du einfach ein Script/Programm schreiben, dass die Rechte überprüft und gegebenenfalls die Datei aus dem Verzeichnis ausliest und an den Browser sendet.
Viele Grüße Novi
Die Kunden kann man per ID son ziemlich genau bestimmen. Man könnte die pdf Datein in einen Ordner packen der diese ID hat und dann diese beim login abrufen. .htacces um diese von außen zu schützen würde ich auch empfehlen.
Die Kunden kann man per ID son ziemlich genau bestimmen. Man könnte die pdf Datein in einen Ordner packen der diese ID hat und dann diese beim login abrufen. .htacces um diese von außen zu schützen würde ich auch empfehlen.
".htaccess" (gemeint ist sicher mod_auth_*) ist kein zuverlässiger Schutz und ganz sicher nicht empfehlenswert - sollte aus irgendwelchen Umständen dieser Schutz versagen, liegen die Dokumente offen im Netz.
Aus diesem Grund ist es _empfehlenswert_ die Dokumente außerhalb des DocumentRoot zu platzieren.
Dokumente in einem durch mod_auth_* geschützen Verzeichnis abzulegen ist höchstens die Ausweichlösung falls man keine bessere Möglichkeit hat.
Hi,
".htaccess" (gemeint ist sicher mod_auth_*) ist kein zuverlässiger Schutz
außer HTTP AUTH kommt natürlich auch noch ein brachiales Deny From All in Frage.
Der Schutz ist natürlich unter den Umständen, die du ansprichst (Anweisungen in der .htaccess werden aus irgendwelchen Gründen nicht berücksichtigt) ebenfalls futsch.
Aus diesem Grund ist es _empfehlenswert_ die Dokumente außerhalb des DocumentRoot zu platzieren.
Ja.
Dokumente in einem durch mod_auth_* geschützen Verzeichnis abzulegen ist höchstens die Ausweichlösung falls man keine bessere Möglichkeit hat.
Einen kleinen Strohhalm gibt's noch, an den man sich klammern kann: Man benennt die Dateien so, dass der Name mit ".ht" beginnt. Diese Dateien sind nämlich auch in der Defaultkonfiguration des Apachen schon ausgenommen und werden weder in einem Verzeichnislisting gezeigt (sollte es einmal dazu kommen), noch auf direkte Anfrage ausgeliefert.
Ciao,
Martin
Einen kleinen Strohhalm gibt's noch, an den man sich klammern kann: Man benennt die Dateien so, dass der Name mit ".ht" beginnt. Diese Dateien sind nämlich auch in der Defaultkonfiguration des Apachen schon ausgenommen und werden weder in einem Verzeichnislisting gezeigt (sollte es einmal dazu kommen), noch auf direkte Anfrage ausgeliefert.
Aber es gibt auch veränderte Konfigurationen, darum warnt die Apache-Doku auch davor das Passwort-File (welches üblicherweise .htpasswd oder ähnliches heisst) im DocumentRoot (oder darunter) liegen zu lassen.
hi,
Frage: Wie kann ich das realisierien, ohne für jeden User den Dateinamen mit kryptischen Zeichen zu versehen (damit andere User den Dateinamen nicht "erraten" können)?
Einen 'Dateinamen' sollte der User gar nicht erst zu Gesicht bekommen, die Datei wird serverseitig erzeugt, wie das geht, haben die Anderen schon beschrieben und wie die (temporär) heißt, ist egal.
Wenn Du ohnehin mit Session arbeitest, programmiere es so, dass der User allenfalls nur die SessID sehen kann (im Cookie).
Hotti