Question

I have a index script that is executed INSIDE the document root thats in:

/var/www/mywebsite/protected-folder/index.php

now I have a directory OUTSIDE the document root that contains a list of subdirectories that have files in:

/var/www/uploads/LIST OF SUBDIRECTORIES/file

When the uploads folder was inside the document root I used this code:

<?php
$dir = "/var/www/uploads";
$list = scandir($dir); /* This function sorts dirs */
$list = array_diff($list,array(".","..","index.php"));

echo "<ol>";
foreach ($list as $file)
{
   if (!is_dir($file)) echo "<li><a href='https://mysite.ca/protected-folder/uploads/$file'>$file</a></li>\n";
}
echo "</ol>";
?>

However this folder needs to be private from public unless logged in and has access to this script.

how can I create a link to the folder that is outside the document root and if the link is clicked on show the files inside that directory?

EDIT: To make my question more clear the uploads folder will have two tiers of subdirectories which will be an unknown number: /var/www/uploads/UNKNOWN LIST OF SUBDIRECTORY LEVEL 1/UNKNOWN SUBDIRECTORIES LEVEL 2/ALL FILES (file can be any file type)

The way this was done before was using apache indexes to allow the user to transverse through the subdirectories. This needs to be secure to prevent direct url access so this is how I want it to work:

  1. List all the first subdirectory links (links to all subdirectory level 1)

  2. Then once the link is clicked on list all subdirectory level 2 folders that are in subdirectory level 1

  3. Finally if that link (subdirectory 2) is clicked on show all the files that are in subdirectory 2

hope that clears things up

Was it helpful?

Solution

The code you have doesn't care if the directory is inside or outside the document root. Just link to a PHP file to retrieve the file itself (instead of a link to the file upload since it's not available). To retrieve a file you just need to grab the contents using a script and output it.

Something like this:

<?php
$path = '/var/www/uploads';
$file = do_something_to_make_this_safe($_POST['file_to_retrieve']);

$type = mime_content_type( $path . '/' . $file );
$contents = file_get_contents($path . '/' . $file);

header('Content-Type: ' . $type);
header('Content-Disposition: attachment;filename=' . $file);
print $contents;

?>

Note you'll need to make sure someone isn't polluting for file path with things like .. to try to access forbidden files. (thus the do_something_to_make_this_safe())

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top