|
Posted by J.O. Aho on 12/15/05 14:14
Sam wrote:
>>> You will need to use a fpassthru()*, this will in it's turn fill up the output
>>> buffer, so you will need to see to that in php.ini you set the execution size
>>> to large enough to be able to hold the largest file in the buffer and still be
>>> able to execute the script itself (+1M to the largest file should be okey).
>
> Thanks for this!
>
> I've been trying to digest what needs to be done over the last couple
> of days :o)
>
> What I can't seem to get my head round is *why* a fpassthru() is
> needed. Can you maybe give me a scenario explaining when and how it
> would actually be used?
Let say we have the file mysong.mp3 that you are selling, then you want to
earn money for each person downloading this file.
If you have it in an accessible directory for the web server with a
document-root of /var/www/html (this means that when going to
http://www.example.net you will access the /var/www/html/index.php) say
/var/www/html/myfiles, then anyone who knows the location of the file and the
filename will be able to download the file without paying you anything.
A person could just type the following in the URL and get your file for free:
http://www.example.net/myfiles/mysong.mp3
If you put your file in the directory /var/www/myfiles, then you can't access
the file with a web browser (without help of a php script), even if you give
the URL:
http://www.example.net/../myfiles/mysong.mp3
you wouldn't be able to access the file in question, even if it would
logically be possible, as the web server wouldn't go out of the /var/www/html
directory and therefore give the user a ERROR page (document-root is like the
root '/' for the web server).
A php script can read a file outside the document-root, as long as the web
server has the right to read the file (as php is executed as the same user as
the web server is run as, of course on unsecure operating systems which don't
have real multiuser environment, the web server can read ALL files), so to
access a file that is outside the document-root, the php script has to read
the file in question and then output the file and an easy way to do this is to
use fpassthru() function, of course you can use any of the other file read
function, as long as you do echo out what you have read.
If you use fpassthru(), then you you can check if the user who is logged into
your web page has the right to download the file or not, if not logged in or
don't have payed for the right to download the file in question, then you can
with an easy header() redirect them to another page where you can ask them to
login/or pay before they download.
Thats why you should use fpassthru(), of course this has dangers too. Say your
download script is download.php and you have the option 'file' to tell which
file you allow to download, this can be done in two ways, the simple and
dangerous way
if(user_okey()) {
$fp = fopen("/var/www/myfiles".$_REQUEST['file'], 'rb');
fpassthru($fp);
exit;
}
In this case someone could access files you don't want them to access, like
http://www.example.net/download.php?file=../../../etc/passwd
This would give the user the user list of real users on the server in question
(if it's running on a *nix system).
Then it's better to have a id translation, either a hardcoded or using a SQL
lookup (the example uses hard coded one):
if(user_okey()) {
switch( $_REQUEST['file'] ) {
case '1':
$filename="/var/www/myfiles/mysong.mp3";
break;
case '2':
$filename="/var/www/myfiles/myfriendssong.mp3";
break;
case '3':
$filename="/var/www/myfiles/myvideo.mpg";
break;
case default:
$filename="/dev/null";
break;
}
$fp = fopen($filename, 'rb');
fpassthru($fp);
exit;
}
NOTE: user_okey() is a made up function that is suppose to check if the user
has the right to download things or not and give a simple true/false return value.
I hope this makes it a bit clear why you should use a function like
fpassthru() (or any of the other file read functions together with some kind
of output function). The examples here are really simple and aren't supposed
to be working 100% in a real script (headers and such are quite important when
wanting to pass files in a script, tak a look at the header() function). The
server in the example will be running a *nix operating system, as I don't
think anything else would suite a web server. Replace www.example.net with
your servers real ip-name.
//Aho
Navigation:
[Reply to this message]
|