[php] Output an Image in PHP

I have an image $file ( eg ../image.jpg )

which has a mime type $type

How can I output it to the browser?

This question is related to php image

The answer is


header('Content-type: image/jpeg');
readfile($image);

<?php

header("Content-Type: $type");
readfile($file);

That's the short version. There's a few extra little things you can do to make things nicer, but that'll work for you.


header("Content-type: image/png"); 
echo file_get_contents(".../image.png");

The first step is retrieve the image from a particular location and then store it on to a variable for that purpose we use the function file_get_contents() with the destination as the parameter. Next we set the content type of the output page as image type using the header file. Finally we print the retrieved file using echo.


You can use finfo (PHP 5.3+) to get the right MIME type.

$filePath = 'YOUR_FILE.XYZ';
$finfo = finfo_open(FILEINFO_MIME_TYPE);
$contentType = finfo_file($finfo, $filePath);
finfo_close($finfo);

header('Content-Type: ' . $contentType);
readfile($filePath);

PS: You don't have to specify Content-Length, Apache will do it for you.


Try this:

<?php
  header("Content-type: image/jpeg");
  readfile("/path/to/image.jpg");
  exit(0);
?>

For the next guy or gal hitting this problem, here's what worked for me:

ob_start();
header('Content-Type: '.$mimetype);
ob_end_clean();
$fp = fopen($fullyQualifiedFilepath, 'rb');
fpassthru($fp);
exit;

You need all of that, and only that. If your mimetype varies, have a look at PHP's mime_content_type($filepath)


    $file = '../image.jpg';
    $type = 'image/jpeg';
    header('Content-Type:'.$type);
    header('Content-Length: ' . filesize($file));
    $img = file_get_contents($file);
    echo $img;

This is works for me! I have test it on code igniter. if i use readfile, the image won't display. Sometimes only display jpg, sometimes only big file. But after i changed it to "file_get_contents" , I get the flavour, and works!! this is the screenshoot: Screenshot of "secure image" from database


You can use header to send the right Content-type :

header('Content-Type: ' . $type);

And readfile to output the content of the image :

readfile($file);


And maybe (probably not necessary, but, just in case) you'll have to send the Content-Length header too :

header('Content-Length: ' . filesize($file));


Note : make sure you don't output anything else than your image data (no white space, for instance), or it will no longer be a valid image.


If you have the liberty to configure your webserver yourself, tools like mod_xsendfile (for Apache) are considerably better than reading and printing the file in PHP. Your PHP code would look like this:

header("Content-type: $type");
header("X-Sendfile: $file"); # make sure $file is the full path, not relative
exit();

mod_xsendfile picks up the X-Sendfile header and sends the file to the browser itself. This can make a real difference in performance, especially for big files. Most of the proposed solutions read the whole file into memory and then print it out. That's OK for a 20kbyte image file, but if you have a 200 MByte TIFF file, you're bound to get problems.


(Expanding on the accepted answer...)

I needed to:

  1. log views of a jpg image and an animated gif, and,
  2. ensure that the images are never cached (so every view is logged), and,
  3. also retain the original file extensions.

I accomplished this by creating a "secondary" .htaccess file in the sub-folder where the images are located.
The file contains only one line:

AddHandler application/x-httpd-lsphp .jpg .jpeg .gif

In the same folder, I placed the two 'original' image files (we'll call them orig.jpg and orig.gif), as well as two variations of the [simplified] script below (saved as myimage.jpg and myimage.gif)...

<?php 
  error_reporting(0); //hide errors (displaying one would break the image)

  //get user IP and the pseudo-image's URL
  if(isset($_SERVER['REMOTE_ADDR'])) {$ip =$_SERVER['REMOTE_ADDR'];}else{$ip= '(unknown)';}
  if(isset($_SERVER['REQUEST_URI'])) {$url=$_SERVER['REQUEST_URI'];}else{$url='(unknown)';}

  //log the visit
  require_once('connect.php');            //file with db connection info
  $conn = new mysqli($servername, $username, $password, $dbname);
  if (!$conn->connect_error) {         //if connected then save mySQL record
   $conn->query("INSERT INTO imageclicks (image, ip) VALUES ('$url', '$ip');");
     $conn->close();  //(datetime is auto-added to table with default of 'now')
  } 

  //display the image
  $imgfile='orig.jpg';                             // or 'orig.gif'
  header('Content-Type: image/jpeg');              // or 'image/gif'
  header('Content-Length: '.filesize($imgfile));
  header('Cache-Control: no-cache');
  readfile($imgfile);
?>

The images render (or animate) normally and can be called in any of the normal ways for images (like an <img> tag), and will save a record of the visiting IP, while invisible to the user.


$file = '../image.jpg';

if (file_exists($file))
{
    $size = getimagesize($file);

    $fp = fopen($file, 'rb');

    if ($size and $fp)
    {
        // Optional never cache
    //  header('Cache-Control: no-cache, no-store, max-age=0, must-revalidate');
    //  header('Expires: Mon, 26 Jul 1997 05:00:00 GMT'); // Date in the past
    //  header('Pragma: no-cache');

        // Optional cache if not changed
    //  header('Last-Modified: '.gmdate('D, d M Y H:i:s', filemtime($file)).' GMT');

        // Optional send not modified
    //  if (isset($_SERVER['HTTP_IF_MODIFIED_SINCE']) and 
    //      filemtime($file) == strtotime($_SERVER['HTTP_IF_MODIFIED_SINCE']))
    //  {
    //      header('HTTP/1.1 304 Not Modified');
    //  }

        header('Content-Type: '.$size['mime']);
        header('Content-Length: '.filesize($file));

        fpassthru($fp);

        exit;
    }
}

http://php.net/manual/en/function.fpassthru.php