Image Data URIs with PHP
If you troll page markup like me, you've no doubt seen the use of data URI's within image src attributes. Instead of providing a traditional address to the image, the image file data is base64-encoded and stuffed within the src attribute. Doing so saves a network request for each image, and if you're the paranoid type, can prevent exposure of directory paths. Since creating data URIs is incredibly easy, let me show you how to do it with PHP.
The PHP
Start by reading in the image using file_get_contents (or any other PHP method you'd like), then convert the image to base64 using base64_encode:
// A few settings
$image = 'cricci.jpg';
// Read image path, convert to base64 encoding
$imageData = base64_encode(file_get_contents($image));
// Format the image SRC: data:{mime};base64,{data};
$src = 'data: '.mime_content_type($image).';base64,'.$imageData;
// Echo out a sample image
echo '
';
With the image data in base64 format, the last step is placing that data within the data URI format, including the image's MIME type. This would make for a good function:
function getDataURI($image, $mime = '') {
return 'data: '.(function_exists('mime_content_type') ? mime_content_type($image) : $mime).';base64,'.base64_encode(file_get_contents($image));
}
The thing to remember is that IE7 and lower don't support data URIs, so keep that in mind if you're considering switching from image paths to data URIs!
You could write whole code for us :)
Btw. Good (Y)
Ups ! Sorry , didn’t see , internet too slow =)
Any chance you know of an existing wordpress plugin that could do the above encoding?
I don’t but I’ll see if I can find a HTML parser that can do it!
Hello,
Very Nice Post :)
But… how to protect other media like videos?
Thanks
Very interesting article. I love the helpful things you write about. Thanks and keep ‘em coming.
I think this technique will not allow caching of images. What say about this?
And what about SEo aspect. I want my images to be crawled and indexed by google, so they appear in image search listings !
You would need to experiment; I don’t know that there’s a definitive answer for that.
Wow, there’s no doubt this method can be useful but the resulting overall code ends up too messy!
Thanks anyway !
No so interesting according to me.
Doing so saves a network request for each image but only the number of
requests. With such a mechanism, no caching system can be used. All images
have to be downloaded again and again for each page view.
At the end, there is much more network data consummation and slowest page
display…
A good (and well thinked) caching policy is the best practice :) :)
It would cache with the web page which is totally appropriate in many cases, just set the cache headers in PHP.
PHP pages are made for dynamic content and data. For example, do you expect:
- the number of unread mail not to be updated on your favorite webmail
- to see your member area even if you’ve just logged out
- your basket not to be updated when you add/remove items
Dynamic content must not be cached
But even if you cache PHP pages, if the same picture appears on multiple pages, it will be cached multiple times…
I still think the best practice is a good cache policy (well tuned) for static content (picture, js, css, ….) and leave users request them only on first visit and on cache expire
Hint for anyone dealing with HTTPS: Internet Explorer 8 (and below, if you have a magic polyfill or something) considers data URIs to be unencrypted resources, thus triggering the famous “This page contains unsecure content” notice.
I never figured out a workaround, so if anyone has any tips I’m all ears!
Isn’t the mime_content_type() function deprecated?
http://www.php.net/manual/en/function.mime-content-type.php
Good point. You could use this function or the suggested PAIR route; I stuck with this function because it’s probably the most supported and doesn’t require an external library.
Nice trick, I have used in my few websites, and would use in my new website jayjalaramext.com too,
But there is one limitations, IE8 and below do not render it, so would have to make IE specific stylesheet and use the image as regular source in it instead of uri 1.
There’s always one browser that doesn’t support it. Tusk /rolleyes
Good post though
Very nice! Is there a way we can get this to process multiple images at once?
There’s a class for handling PHP data URLs that I’ve been using for a project, http://www.flyingtophat.co.uk/blog/27/using-data-uris-in-php
I find it easier than calling numerous PHP functions.