WebsiteBaker Community Forum

WebsiteBaker Support (2.8.x) => Droplets & Snippets => Topic started by: pcwacht on March 09, 2010, 02:14:09 PM

Title: filedownload protect with .htaccess and php code
Post by: pcwacht on March 09, 2010, 02:14:09 PM
You have some files wich are only for the registred visitors and you don't want any non registred visitor to get the file

Steps:
1 - create a file in the root of your installation and call it : WB-securedownload
Code: [Select]
<?php
// Secure download for WebsiteBaker
// original by VotreEspace see thread : https://forum.WebsiteBaker.org/index.php/topic,16282.msg106944.html#msg106944
// adapted and improved by PCWacht (march-2010)
//
// Use as : WB-securedownload.php?file=/media/thisdocument.doc
// 
//
if (isset($_GET[&#39;file&#39;])) {
require("config.php");
# code the url
$DEC urldecode($_GET[&#39;file&#39;]);
# set unallowed file, so nobody want to read /config.php or something
$unallowed_to_read = array(&#39;php&#39;,&#39;html&#39;,&#39;htm&#39;,&#39;htaccess&#39;);
#Check for images, they should be shown
$allowed_to_read = array(&#39;jpg&#39;,&#39;gif&#39;,&#39;png&#39;);
# remove any attempt to back up your folders
$fichier str_replace(&#39;../&#39;,&#39;&#39;,WB_PATH.&#39;/media/&#39;.urldecode($_GET[&#39;file&#39;]));
if(isset($_SESSION[&#39;USER_ID&#39;]) && SESSION_STARTED) {
if(file_exists($fichier) && (!in_array(end(explode(&#39;.&#39;,$fichier)),$unallowed_to_read))) {
header("Content-Type: " mime_content_type($fichier));
header("Content-Length: " filesize($fichier));
header("Content-Transfer-Encoding: binary");
header("Cache-Control: private");
header(&#39;Content-Disposition: attachment; filename="&#39;.end(explode(&#39;/&#39;,$DEC)).&#39;"&#39;);
echo file_get_contents($fichier);
} else {
# in case of absent file or attempt at hacking
echo &#39;oups&#39;;
}
} else {
if(file_exists($fichier) && (in_array(end(explode(&#39;.&#39;,$fichier)),$allowed_to_read))) {
header("Content-Type: " mime_content_type($fichier));
header("Content-Length: " filesize($fichier));
header("Content-Transfer-Encoding: binary");
header("Cache-Control: private");
header(&#39;Content-Disposition: attachment; filename="&#39;.end(explode(&#39;/&#39;,$DEC)).&#39;"&#39;);
echo file_get_contents($fichier);
} else {
# not logged  in and no picture? forbidden! 
header(&#39;HTTP/1.0 403 forbidden&#39;, TRUE, 403);
die(&#39;<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN"> 
<html><head
<title>403 Forbidden</title
</head><body
<h1>FORBIDDEN</h1
<p>Without being logged in you don&#39;t have permission to fetch <b>&#39;.urldecode($_GET[&#39;file&#39;]).&#39;</b> from this server server.</p> 
<p><a href="/account/login.php">Click for login.</a></p>
</body></html> &#39;);
}
}
}else{
header(&#39;Location: ./&#39;);
}
?>


2 - create a .htaccess file in the foor of your wb installation in it:
Code: [Select]
RewriteEngine on
RewriteRule ^media/(.*)\.(.*)$ /WB-securedownload.php?file=$1.$2 [R,L]
tip - - change the path /WB-securedownload to /wb-path/WB-securedownload if needed

The way it works
1 with a htaccess rewriterule we test to see if something is needed from teh media folder, if so redirect it to a script so we can test it
examplë:
http://www.someserver.com/media/somefolder/somefile.doc
will become:
http://www.someserver.com/WB-securedownload?file=somefolder/somefile.doc

The script in WB-securedir will test to see if:
1 - the parameter file was given
2 - if user is logged in
3 - if it is a picture, then show it


Have fun,
John
Title: Re: filedownload protect with .htaccess and php code
Post by: Ralph on June 21, 2010, 12:46:21 PM
Hallo John,

ich habe versucht Dein Beispiel in meine Seite einzubauen, leider ohne Erfolg. In dem Media Ordner hab ich PDF Dateien (auch Unterordner). Ich will verhindern das man ohne Anmeldung auf die PDF zugreifen kann wenn man den direkten Pfad kennt.

Die Datei 'WB-securedownload.php' hab ich ins Rootverzeichniss (www.xyz.de/WB-securedownload.php) des Webservers kopiert und die htaccess in das Rootverzeichnis der WebsiteBaker Installation.

Was mache ich falsch?

Leider ist mein Englisch sooo schlecht, das mir nichts übrig bleibt als in Deutsch anzufragen ob Du mir helfen kannst.

Gruß
Ralph
Title: Re: filedownload protect with .htaccess and php code
Post by: Ralph on June 22, 2010, 03:22:59 PM
Hi John,
I have a little now can achieve. But after calling a file, whether loggin or not I get a 404 Not Found, and the URL that is generated looks like this:
http://www.xyz.de/var/www/vhosts/xyz.de/WB-securedownload.php?file=download_gallery/xy.pdf

please help me

Ralph
Title: Re: filedownload protect with .htaccess and php code
Post by: kweitzel on June 22, 2010, 03:51:56 PM
That does sound as if you have the WB_URL in front of the WB_PATH ... did you just copy the script and the htaccess or did you change it?

cheers

Klaus
Title: Re: filedownload protect with .htaccess and php code
Post by: pcwacht on June 22, 2010, 03:56:18 PM
Schau dir die .htaccess nach weil die linke:

http://www.xyz.de/var/www/vhosts/xyz.de/WB-securedownload.php?file=download_gallery/xy.pdf

soll

http://www.xyz.de/WB-securedownload.php?file=download_gallery/xy.pdf

sein

Ich glaube die .htaccess macht wass falsch, vielleicht hatte es etwas mit symlinks zu machen.

versuche mal diese .htaccess

Quote
Options +FollowSymlinks
RewriteEngine on
RewriteRule ^media/(.*)\.(.*)$ /WB-securedownload.php?file=$1.$2 [R,L]

Wenn es nuhr fur einer unterordner unter media geben soll:

Quote
Options +FollowSymlinks
RewriteEngine on
RewriteRule ^media/unterordner/(.*)\.(.*)$ /WB-securedownload.php?file=$1.$2 [R,L]

Ich hoffe du schaft es.

Spass,
John


Title: Re: filedownload protect with .htaccess and php code
Post by: pcwacht on June 22, 2010, 03:59:15 PM
RewriteBase /
is needed as well

try:
Code: [Select]
Options +FollowSymlinks
RewriteEngine on
RewriteBase /
RewriteRule ^media/(.*)\.(.*)$ /WB-securedownload.php?file=$1.$2 [R,L]

John
Title: Re: filedownload protect with .htaccess and php code
Post by: Ralph on June 22, 2010, 04:35:58 PM
with RewriteBase / sees the URL as it should be like this but it is a Error 400 "Bad Request
Your browser sent a request that this server could not understand.
Client sent malformed Host header"

and now?  :x
Title: Re: filedownload protect with .htaccess and php code
Post by: pcwacht on June 22, 2010, 04:40:55 PM
So mit RewriteBase /
die url rewriting geht gut?

Sie bekommen etwas als : http://www.xyz.de/WB-securedownload.php?file=download_gallery/xy.pdf


Die Bad Request komt von die WB-securedownload.php ??
sei sicher das die WB-securedownload stimmt mit dass wass ich als ersten geschrieben habe.
Wenn nur etwas fehlt bekommt du das

Sie könte es aber testen mit:
WB-securedownload.php?file=einer.pdf


Spass,
John
Title: Re: filedownload protect with .htaccess and php code
Post by: Ralph on June 23, 2010, 09:20:33 AM
Thanks John,

in the. htaccess I had before / WB securedownload.php still do .. / or he calls on not. Now looks like this:

Options +FollowSymlinks
RewriteEngine on
RewriteBase /
RewriteRule ^media/(.*)\.(.*)$ ../WB-securedownload.php?file=$1.$2 [R,L]

The / WB-securedownload.php (I have no changes from you) creates now this url:

Url: http://www.xyz.de/WB-securedownload.php?file=download_gallery/xy.pdf

When you call, whether logged in or not here comes this error:

Bad Request 400
Your browser sent a request that this server could not understand.
Client sent malformed Host header

Can it deal here with an error:
header("Content-Type: " . mime_content_type($fichier));
Because there are pdf?

If I put both scripts in the WB folder and the two .. remove, then comes the error "not found".

I know now go no further
Title: Re: filedownload protect with .htaccess and php code
Post by: Ralph on June 30, 2010, 06:31:17 PM
Hallo John,
nochmals Danke für Deine Unterstützung, hab jetzt es jetzt zum Laufen gebracht (ein anderer Profi hat mich unterstützt :wink:).

Ich habe beide Dateien in das Root Verzeichnis der WB Installation kopiert, mit der .htaccsess war alles in Ordnung. In den WB-Secure Script hatten sich zwei kleine Fehler eingeschlichen. Im letzten else Zweig beim don't das Hochkomma und weiss ich nicht mehr daher hier meine geänderte Fassung

Code: [Select]
<?php
// Secure download for WebsiteBaker
// original by VotreEspace see thread : https://forum.WebsiteBaker.org/index.php/topic,16282.msg106944.html#msg106944
// adapted and improved by PCWacht (march-2010)
//
// Use as : WB-securedownload.php?file=/media/thisdocument.doc
// 
//

if (isset($_GET[&#39;file&#39;])) {
require("config.php");
# code the url
$DEC urldecode($_GET[&#39;file&#39;]);
# set unallowed file, so nobody want to read /config.php or something
$unallowed_to_read = array(&#39;php&#39;,&#39;html&#39;,&#39;htm&#39;,&#39;htaccess&#39;);
#Check for images, they should be shown
$allowed_to_read = array(&#39;jpg&#39;,&#39;gif&#39;,&#39;png&#39;);
# remove any attempt to back up your folders
$fichier str_replace(&#39;../&#39;,&#39;&#39;,WB_PATH.&#39;/media/&#39;.urldecode($_GET[&#39;file&#39;]));
if(isset($_SESSION[&#39;USER_ID&#39;]) && SESSION_STARTED) {
if(file_exists($fichier) && (!in_array(end(explode(&#39;.&#39;,$fichier)),$unallowed_to_read))) {
header("Content-Type: " mime_content_type($fichier));
header("Content-Length: " filesize($fichier));
header("Content-Transfer-Encoding: binary");
header("Cache-Control: private");
header(&#39;Content-Disposition: attachment; filename="&#39;.end(explode(&#39;/&#39;,$DEC)).&#39;"&#39;);
echo file_get_contents($fichier);
} else {
# in case of absent file or attempt at hacking
echo &#39;oups&#39;;
}
} else {
/*if(file_exists($fichier) && (in_array(end(explode(&#39;.&#39;,$fichier)),$allowed_to_read))) {
header("Content-Type: " . mime_content_type($fichier));
header("Content-Length: " . filesize($fichier));
header("Content-Transfer-Encoding: binary");
header("Cache-Control: private");
header(&#39;Content-Disposition: attachment; filename="&#39;.end(explode(&#39;/&#39;,$DEC)).&#39;"&#39;);
echo file_get_contents($fichier);
} else {*/
# not logged  in and no picture? forbidden! 
header(&#39;HTTP/1.0 403 forbidden&#39;, TRUE, 403);
die(&#39;<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN"> 
<html><head
<title>403 Forbidden</title
</head><body
<h1>FORBIDDEN</h1
<p>Without being logged in you dont have permission to fetch <b>&#39;.urldecode($_GET[&#39;file&#39;]).&#39;</b> from this server server.</p> 
<p><a href="/vWB_Verzeichnis/account/login.php">Click for login.</a></p>
</body></html> &#39;);
}
//}
}else{
header(&#39;Location: ./&#39;);
}
?>


Was mich schon wundert ist, dass diesem Problem der Verzeichnissicherhe it hier nicht mehr Aufmerksamkeit geschenkt wird bzw. scheint es den Nutzern noch nicht augefallen zu sein, dass man über den absoluten Pfad alles bekommen kann. Egal Problem gelöst , nehmen wir die nächten in Angriff. Ansonsten macht mir WB sehr viel Spass, man muß sich eben reindenken. Also Danke für Eure Hilfe bis bald

Ralph
Title: Re: filedownload protect with .htaccess and php code
Post by: DarkViper on June 30, 2010, 08:04:56 PM
Quote
Was mich schon wundert ist, dass...

What always makes me surprised is, that...
... such a lot of people use this three characters CMS... without knowing about the real meaning of.   :?

Read this... (https://forum.WebsiteBaker.org/index.php/topic,18596.msg124072.html#msg124072)
Title: Re: filedownload protect with .htaccess and php code
Post by: Ralph on June 30, 2010, 08:39:33 PM
Hallo DarkViper,
wie ich schon gesagt habe, ist mein Englisch grotten schlecht aber wegen deinem Kommentar ... such a lot of people use this three characters CMS... without knowing about the real meaning of. bin ich ja hier um Fragen zu stellen. Was nützt ein Super CMS wenn es bestimmte Sicherheitsfragen gibt. Aber an dieser Stelle genug, ich denke Websitbaker mit seiner Gemeinschaft hat das Zeug früher oder Später zü den ganz Großen zu gehören.

Gruß Ralph
Title: Re: filedownload protect with .htaccess and php code
Post by: Hans Toolbox on June 30, 2010, 08:49:09 PM
Es gibt in diesem Falle keine Sicherheitsfragen, da man -wie schon gesagt- ein CMS vor sich hat.
Will man "Dateien schützen", die nicht für die Öffentlichkeit bestimmt sind, greift man zu entsprechenden Systemen.
Title: Re: filedownload protect with .htaccess and php code
Post by: pcwacht on June 30, 2010, 09:13:38 PM
Quote
Will man "Dateien schützen", die nicht für die Öffentlichkeit bestimmt sind, greift man zu entsprechenden Systemen.
Hmmm.. nicht meiner meinung, es gibt viele wegen zum schutzen

Einer ist dieses mit htaccess
Ein andere wäre zum beispiel ein directory zu machen ausser das html bereich und es mit php control zu ubergeben
Ein andere ist um die dateien ins database zu verlegen.

Genau dass ist das beste an WB, ins herz ist es einfach, aber powerfull genug um es mit ein wenig code dass zu machen was man braucht.
WB kann fast alles! Aber nicht nur mit die core, stimmt.

John
Title: Re: filedownload protect with .htaccess and php code
Post by: Hans Toolbox on June 30, 2010, 10:14:31 PM
htaccess ist auf Apache beschränkt.
WebsiteBaker wird von mir empfohlen, weil es auf NGINX, LIGHTTPD oder *beliebig anderen http-Diensten funktioniert. Nicht anderes erwarte ich auch von einem PHP-CMS. Das ist eine hervorstechende Eigenschaft von WebsiteBaker, die leider nur von wenigen erkannt wird. WB läuft überall!
*: Serverspezifisches File-Management in WB ist überflüssig oder dürfte dann etwas umfangreicher ausfallen  :evil:
Wenn WB weiterhin unabhängig funktionieren soll ist Dein Vorschlag "php control" richtungsweisend. Zwei meiner Anwender haben auch  ihre Medien-Dateien unterhalb von wwwroot und verwalten diese über ein Script.

*=Textänderungen

Deine Lösung (htaccess/php) ist und bleibt natürlich trotzdem eine wirklich tolle (+tricky) !

There is an English forum here, I finish my German responses
Title: Re: filedownload protect with .htaccess and php code
Post by: Don Martin on February 15, 2013, 05:10:04 PM
Ich hatte Probleme mit der mime_content_type($fichier) Funktion im Code. Diese ist eine "veraltet" Funktion.
Hilfe zu diesem Problem habe ich hier gefunden: https://forum.WebsiteBaker.org/index.php/topic,16282.0.html
Title: Re: filedownload protect with .htaccess and php code
Post by: Hans on February 17, 2013, 11:46:20 PM
Hallo Don

es wäre schön wenn Du die Code publizieren wolltest (Code ohne die veraltete Funktion). Ich bin ein kompletter NOOB und dankbar wenn du es mit mir (uns) teilen wolltest.

Und Verzeihung für mein "Deutsch" ;-)
Hans
Title: Re: filedownload protect with .htaccess and php code
Post by: Don Martin on February 20, 2013, 08:58:19 AM
Hallo Hans

Ich habe den folgenden Code benutzt um mein gesamtes Media Verzeichnis zu schützen. Ich hoffe diese Informationen helfen dir weiter.

Code: [Select]
<?php
// Secure download for WebsiteBaker
// original by VotreEspace see thread : https://forum.WebsiteBaker.org/index.php/topic,16282.msg106944.html#msg106944
// adapted and improved by PCWacht (march-2010)
//
// Use as : WB-securedownload.php?file=/media/thisdocument.doc
// 
//

if (isset($_GET['file'])) {
require("config.php");
if(!function_exists('mime_content_type')) {
function mime_content_type($filename) {
$mime_types = array(

'txt' => 'text/plain',
'htm' => 'text/html',
'html' => 'text/html',
'php' => 'text/html',
'css' => 'text/css',
'js' => 'application/javascript',
'json' => 'application/json',
'xml' => 'application/xml',
'swf' => 'application/x-shockwave-flash',
'flv' => 'video/x-flv',

// images
'png' => 'image/png',
'jpe' => 'image/jpeg',
'jpeg' => 'image/jpeg',
'jpg' => 'image/jpeg',
'gif' => 'image/gif',
'bmp' => 'image/bmp',
'ico' => 'image/vnd.microsoft.icon',
'tiff' => 'image/tiff',
'tif' => 'image/tiff',
'svg' => 'image/svg+xml',
'svgz' => 'image/svg+xml',

// archives
'zip' => 'application/zip',
'rar' => 'application/x-rar-compressed',
'exe' => 'application/x-msdownload',
'msi' => 'application/x-msdownload',
'cab' => 'application/vnd.ms-cab-compressed',

// audio/video
'mp3' => 'audio/mpeg',
'qt' => 'video/quicktime',
'mov' => 'video/quicktime',

// adobe
'pdf' => 'application/pdf',
'psd' => 'image/vnd.adobe.photoshop',
'ai' => 'application/postscript',
'eps' => 'application/postscript',
'ps' => 'application/postscript',

// ms office
'doc' => 'application/msword',
'rtf' => 'application/rtf',
'xls' => 'application/vnd.ms-excel',
'ppt' => 'application/vnd.ms-powerpoint',

// open office
'odt' => 'application/vnd.oasis.opendocument.text',
'ods' => 'application/vnd.oasis.opendocument.spreadsheet',
);

$ext strtolower(array_pop(explode('.',$filename)));
if (array_key_exists($ext$mime_types)) {
return $mime_types[$ext];
}
elseif (function_exists('finfo_open')) {
$finfo finfo_open(FILEINFO_MIME);
$mimetype finfo_file($finfo$filename);
finfo_close($finfo);
return $mimetype;
}
else {
return 'application/octet-stream';
}
}
}
# code the url
$DEC urldecode($_GET['file']);
# set unallowed file, so nobody want to read /config.php or something
$unallowed_to_read = array('php','html','htm','htaccess');
#Check for images, they should be shown
$allowed_to_read = array('jpg','gif','png');
# remove any attempt to back up your folders
$fichier str_replace('../','',WB_PATH.'/media/'.urldecode($_GET['file']));
if(isset($_SESSION['USER_ID']) && SESSION_STARTED) {
if(file_exists($fichier) && (!in_array(end(explode('.',$fichier)),$unallowed_to_read))) {
header("Content-Type: " mime_content_type($fichier));
header("Content-Length: " filesize($fichier));
header("Content-Transfer-Encoding: binary");
header("Cache-Control: private");
header('Content-Disposition: attachment; filename="'.end(explode('/',$DEC)).'"');
echo file_get_contents($fichier);
} else {
# in case of absent file or attempt at hacking
echo 'oups';
}
} else {
/*if(file_exists($fichier) && (in_array(end(explode('.',$fichier)),$allowed_to_read))) {
header("Content-Type: " . mime_content_type($fichier));
header("Content-Length: " . filesize($fichier));
header("Content-Transfer-Encoding: binary");
header("Cache-Control: private");
header('Content-Disposition: attachment; filename="'.end(explode('/',$DEC)).'"');
echo file_get_contents($fichier);
} else {*/
# not logged  in and no picture? forbidden! 
header('HTTP/1.0 403 forbidden'TRUE403);
die('<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN"> 
<html><head> 
<title>403 Forbidden</title> 
</head><body> 
<h1>FORBIDDEN</h1> 
<p>Without being logged in you dont have permission to fetch <b>'
.urldecode($_GET['file']).'</b> from this server.</p> 
<p><a href="/pages/deu_top/haendler-login.php">Click for login.</a></p>
</body></html> '
);
}
//}
}else{
header('Location: ./');
}

?>
Title: Re: filedownload protect with .htaccess and php code
Post by: DarkViper on February 20, 2013, 12:20:15 PM
Verlass Dich bitte nicht auf diesen Codeschnipsel:
Code: [Select]
<?php
# remove any attempt to back up your folders
$fichier str_replace('../','',WB_PATH.'/media/'.urldecode($_GET['file']));

Das ist sehr einfach zu umgehen. Es genügt, im Request anstatt des Slashes einen Backslash einzugeben. Oder aber anstatt '../' die Zeichenfolge '..././'.
Relativ sicher lässt sich ein extern eingegebener Pfad mittels realpath() und stripos() überprüfen.

Code: [Select]
<?php
$sMediaDir str_replace('\\''/'WB_PATH.'/media');
if( ($fichier realpath(WB_PATH.'/media/'.urldecode($_GET['file']))) !== false) {
$fichier str_replace('\\''/'$fichier);
if( stripos($fichier$sMediaDir) !== ) {
// ungueltiger Pfad
}
}else {
// ungueltiger Pfad
}
dieser Schnipsel bringt einen Fehler, wenn ein fehlerhafter Pfad übergeben wird oder die gesuchte Datei nicht innerhalb des Mediaverzeichnisses liegt.
Title: Re: filedownload protect with .htaccess and php code
Post by: hoerts on February 24, 2013, 09:15:37 PM
Er der nogen som kan forklare mig hvad der står i denne tråd, som er skrevet i forummet for engelsk talende?