Hi all

I have a system which has images stored outside of web root. For the life of me I cannot get the images to display in my webpage unless I move the folders inside of web root (which is not an option).

I have added a check to see if the path is readable and all is OK, so I cannot see why this is not working:

<?php
		if (!empty($param['imagename'])) {
			if (is_readable('/home/sites/mydomain.com/secureimages/' . $param['imagename'])) {
				echo "ITS READABLE!!!!!!!!!!!!!!!!";
			}
?>
			<div class="questionimage">
            	<img src="<?php echo '/home/sites/mydomain.com/secureimages/' . $param['imagename']; ?>" alt="">
            </div>
<?php			
		}

Any thoughts as to why this is?

Thanks for reading.

    Server settings, probably? Apache, for one, will usually deny reading anything outside the web root. And that is as it should be ... what's to prohibit the web server from, say, reading /etc/master.passwd?

    I suppose you could write a script that would:

    1. Obtain the image location from the caller.
    2. Output the needed header data and the data using something like file_get_contents() ...

    Then your SRC attribute in the HTML would just point to your script with the needed params....

      There's a reason it's called the web root; anything not inside of it can't be accessed. (Otherwise, what would be the point of having one in the first place?)

      Out of curiosity, why can't you simply move the images that you want to be accessible into an accessible location?

        (PS: I guess I just sort of reiterated what the first reply suggested. 🙂 )

        If they need to be outside of the web root hierarchy for some reason, you can create an image-server script that you would call as the src value of the relevant img tag:

        <img src='image_server.php?name=<?php echo urlencode($image_name); ?>' alt='' />
        

        At it's simplest, with probably not enough built-in security, image_server.php would be something like:

        <?php
        if(!empty($_GET['name'])) {
          $name = basename($_GET['name']);
          $path = '/path/to/images/';
          if(file_exists($path.$name) and is_readable($path.$name)) {
            header('Content-Type: image/jpeg');
            readfile($path.$name);
            exit;
          }
        }
        header("HTTP/1.0 404 Not Found");
        
          bradgrafelman;11034425 wrote:

          Out of curiosity, why can't you simply move the images that you want to be accessible into an accessible location?

          Well the system is made up of two systems on two domains but on the same dedicated server, first is the admin site and second is a user site. Its essentially an assessment system for users to take tests but the tests are administered by a tutor. The images contain sensitive information and are uploaded via the admin system. My thinking was that these should be stored outsid of the root to prevent any users trying to get direct access to them and share the images with other users who could potentially take the tests in the future.

          Is there a safe way of storing the images within web root?

            condoug;11034455 wrote:

            Is there a safe way of storing the images within web root?

            That obviously depends on the definition of "safe" ... as you've defined it above, I'd say the answer is "no, but maybe" ... because anything under the web root that the server can access, in theory, a user of the server can access. The exception might be in the case of server-based access controls (but I don't know very much about them ... Apache, for example, has several flavors of access control).

            For a quick (and dirty?) solution that works, the image-server idea isn't a overly bad one, but the potential difficulty I see is that if you're trying to be safe from unscrupulous power-users, they still might be able to analyze your HTML source and pull up the images. You might have to do some work with $_SESSION or similar, ensuring that only logged-in users could access the resource...

              A very good reason to store images outside the web root is if you do not want visitors to be able to see them unless they are logged in. If you have any kind of asset (image, javascript, mp3 file, video) that you want to protect from visitors for any reason, it's probably a good idea to have these objects outside the web root and grant access to them by writing a PHP script that coughs them up only if a user meets your criteria.

              Nogdog's recommendation looks pretty good to me. You can make an <img> tag whose src attribtute refers to a PHP script and not the original image and that PHP script would enforce your restrictions. If access is allowed, [man]readfile[/man] is a good basica way to cough up an image/mp3/video, etc:

              <img src="my_php_script.php?img=some_image.jpg">

              One thing to keep in mind is that while your web server can only serve files that are in the webroot, a PHP script within your web root might be able to read stuff outside of your web root. [man]is_readable[/man] tells you what your PHP script can read, not what the web server can serve in response to a request.

                And the ongoing principle to keep in mind is that URLs are not file paths.

                  Write a Reply...