Monthly Archives: February 2011

Watermarks in our images with PHP and mod_rewrite

Imagine you have a set of images and you need to add watermark to all of them. You can do the work with an image editor (Gimp or Photoshop for example). It’s easy work but if your image library is big, the easy work become into hard. But imagine again you need to add a dynamic watermark, let’s say the current timestamp. To solve this problem we can use PHP’s GD image function set.

The idea is simple. Instead of opening directly the image, we are going to open a PHP script. This PHP script will open the original image file with imagecreatefromjpeg, add the footer and flush the new image to the browser with the properly headers.

But I don’t want to rewrite all the anchor’s hrefs within my HTML files. Because of that I’m going to use the same trick I used in my one of my posts. With a simple .htaccess in our jpg’s folder, our apache’s mod_rewrite will do work for us:

RewriteEngine on
RewriteRule !\.(php)$ watermark.php

And now our PHP script called watermark.php

<?php
$uri = $_SERVER['REQUEST_URI'];
$documentRoot = $_SERVER['DOCUMENT_ROOT'];
$filename = $documentRoot . $uri;
if (realpath(__FILE__) == realpath($filename)) {
    exit();
}
$stringSize = 3;
$footerSize = ($stringSize==1) ? 12 : 15;
$footer = date('d/m/Y H:i:s');

list($width, $height, $image_type) = getimagesize($filename);
$im = imagecreatefromjpeg($filename);
imagefilledrectangle (
        $im,
        0,
        $height,
        $width,
        $height - $footerSize, imagecolorallocate($im, 49, 49, 156));

imagestring($im,
        $stringSize,
        $width-(imagefontwidth($stringSize)*strlen($footer)) - 2,
        $height-$footerSize,
        $footer,
        imagecolorallocate($im, 255, 255, 255));

header( 'Content-Type: image/jpeg' );
imagejpeg($im);

Simple, isn’t it? You can change my blue footer with a your logo. Easy with PHP’s gd functions. Of course you need to have your PHP compiled with GD support.

Original image:

After transformation:

Speed up page page load combining javascript files with PHP

One of the golden rules when we want a high performance web site is minimize the HTTP requests. Normally we have several JavaScript files within our projects. It’s a very good practice to combine all our JavaScript files into an only one file. We can do it manually. Not a hard work. We only need to copy and paste the source files into our single js file. There’s even tools to do it. You can have look to Yslow (if you don’t know it yet). That’s a good solution if your project is finished. But if your project is alive and you are changing it, it’s helpful to spare your JavaScript files between several files. It’s good to organize them (at least for me). So we need to choose between high performance and development comfort. Because of that I like to use the simple script I’m going to show now. Let’s start.

The idea is the following one. Normally I have all js files into a folder called js (original isn’t?). I also have a development server and a production one (really original again, isn’t it?). When I’m developing my application I like to have my js files separated and in a human readable way (I’m human), but in production I want to combine them and even minimized and gziped to improve the performance.

The script I have is a simple script that combines all the JavaScript files, minimizes and gzips.

//js.php
require 'jsmin.php';

function checkCanGzip(){
    if (array_key_exists('HTTP_ACCEPT_ENCODING', $_SERVER)) {
        if (strpos($_SERVER['HTTP_ACCEPT_ENCODING'], 'gzip') !== false) return "gzip";
        if (strpos($_SERVER['HTTP_ACCEPT_ENCODING'], 'x-gzip') !== false) return "x-gzip";
    }
    return false;
}

function gzDocOut($contents, $level=6){
    $return = array();
    $return[] = "\x1f\x8b\x08\x00\x00\x00\x00\x00";
    $size = strlen($contents);
    $crc = crc32($contents);
    $contents = gzcompress($contents,$level);
    $contents = substr($contents, 0, strlen($contents) - 4);
    $return[] = $contents;
    $return[] = pack('V',$crc);
    $return[] = pack('V',$size);
    return implode(null, $return);
}

$ite = new RecursiveDirectoryIterator(dirname(__FILE__));
foreach(new RecursiveIteratorIterator($ite) as $file => $fileInfo) {
    $extension = strtolower(pathinfo($file, PATHINFO_EXTENSION));
    if ($extension == 'js') {
        $f = $fileInfo->openFile('r');
        $fdata = "";
        while ( ! $f->eof()) {
            $fdata .= $f->fgets();
        }
        $buffer[] = $fdata;
    }
}

$output = JSMin::minify(implode(";\n", $buffer));

header("Content-type: application/x-javascript; charset: UTF-8");
$forceGz    = filter_input(INPUT_GET, 'gz', FILTER_SANITIZE_STRING);
$forcePlain = filter_input(INPUT_GET, 'plain', FILTER_SANITIZE_STRING);

$encoding = checkCanGzip();
if ($forceGz) {
    header("Content-Encoding: {$encoding}");
    echo gzDocOut($output);
} elseif ($forcePlain) {
    echo $output;
} else {
    if ($encoding){
        header("Content-Encoding: {$encoding}");
        echo GzDocOut($output);
    } else {
        echo $output;
    }
}

As you can see the script checks recursively all the js files inside one folder, combine them and also use jsmin library for PHP to improve the download time in the browser.

It’s very easy now when we’re building our HTML file switch from one js file to another. Here you can see an example with Smarty template engine:

<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
        <title></title>
    </head>
    <body>
        Hello World
{if $dev}
        <script src="js1.js" type="text/javascript"></script>
        <script src="js2.js" type="text/javascript"></script>
        <script src="xxx/js1.js" type="text/javascript"></script>
{else}
        <script src="js.php" type="text/javascript"></script>
{/if}
    </body>
</html>

Yes. I know. There’s a problem with this solution. Maybe we’ve improved the client side performance reducing the number of HTTP requests but, what about our server side performance? We’ve changed from serving static js files to dinamic PHP file. Now our server’s CPU will work more. Another great hight performance golden rule is to place static files into a server dedicated to serve static files (without PHP support). Whit this golden rule we help to the browser to perform multiple downloads and also we reduce the use of CPU (static server will not instance any PHP session).

So a better solution is the offline generation of the static js file when we deploy the application. I do it with a simple curl at command line.

curl http://nov/js/js.php -o jsfull.minified.js

So the smarty template will change to

<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
        <title></title>
    </head>
    <body>
        Hello World
{if $dev}
        <script src="js1.js" type="text/javascript"></script>
        <script src="js2.js" type="text/javascript"></script>
        <script src="xxx/js1.js" type="text/javascript"></script>
{else}
        <script src="jsfull.minified.js" type="text/javascript"></script>
{/if}
    </body>
</html>

It’s also a good solution put a prefix in our JavaScript file and change it each time we build it (easy to automate) to ensure the cache renew.

<script src="jsfull.minified.20110216.js" type="text/javascript"></script>

And yes we can use the same trick with our css files.

Function decorators in PHP with PHPDoc and Annotations

This days I’m playing with annotations in PHP. PHP, at least just now, doesn’t support annotations natively like Java. I hope it will be available in next versions but if we want to use them already, we need to create “fake” annotations within PHPDoc. We also have another problem. The PHP’s built-in’s reflection functions cannot parse properly PHPDoc’s annotations but hopefully we have a great library called addendum to do this.

Last year I posted an article called “Things I miss in PHP: Function decorators”. I wanted to solve something that I miss in PHP. Function decorators. A great feature we’ve got in python world. Now I will try to simulate function decorators in PHP with annotations. Let’s start:

The idea is to solve the same problem I had when I wrote the previous article. I want to protect the execution of certain functions in a class to only being executed if the user is logged on. The functions are public. In the previous solution I my classes implement one interface or another if I wanted to ensure that the functions are really public for everyone or if user need to be logged on. The solution with interfaces is clean and simple (no extra libraries need and no reflection need too). The problem is that I can use it only for all the functions of the class. If I want to mark only one function as “only for logged users” I need to divide the class into two classes, one implementing one interface and the second one another interface. With function decorators I can mark only one function within a class. Let’s show the code:

Imagine we have the following class. We are going to play with decorators in the function hello:

class Dummy
{
    public function gonzalo()
    {
        echo "decorator\n";
        return true;
    }

    public function gonzalo2()
    {
        echo "decorator2\n";
        return true;
    }

    public function gonzalo3()
    {
        echo "post2\n";
        return true;
    }

    /** 
     * @PreDispatch("gonzalo") 
     * @PreDispatch("gonzalo2") 
     * @PostDispatch("gonzalo3") 
     * */
    public function hello($name)
    {
        echo "Hello {$name}";
    }
}

And if we include the following library (I called NewNew)

include "addendum/annotations.php";

class PreDispatch extends Annotation {}
class PostDispatch extends Annotation {} 

class NewNew
{
    private $_instance;

    function __construct($instance)
    {
        $this->_instance = $instance;
    }

    static function factory($instance)
    {
        return new self($instance);
    }

    function __call($method, $args)
    {
        $reflectionMethod = new ReflectionAnnotatedMethod(get_class($this->_instance), $method);
        $continue = true;
        $out = null;
        foreach ($reflectionMethod->getAllAnnotations('PreDispatch') as $decorator) {
            $continue = call_user_func_array(array($this->_instance, $decorator->value), $args);
            if ($continue !== true) break;
        }
        
        if ($continue === true) {
            $out = call_user_func_array(array($this->_instance, $method), $args);
        
            foreach ($reflectionMethod->getAllAnnotations('PostDispatch') as $decorator) {
                $continue = call_user_func_array(array($this->_instance, $decorator->value), $args);
                if ($continue === false) break;
            }
        }

        return $out;
    }
}

As you can see the idea is to call functions annotated as PreDispatch before calling the real function and annotated as PostDispatch before. Those decorator function must return true. If the return value in not true the execution flow will break and next calls will be disabled

And now if we execute the following code:

/** @var Dummy */
$dummy = new NewNew(new Dummy);
echo $dummy->hello("Gonzalo");

we will get:

decorator
decorator2
Hello Gonzalo
post2

OK my decorators are not exactly the same than Phython’s ones, but they meet my requirements.

Now we are going to implement another example.

abstract class Decorators
{
    public function check($user)
    {
        if ($user == 'gonzalo') {
            return true;
        } else {
            return false;
        }
    }
}
class Dummy2 extends Decorators
{
    /** 
     * @PreDispatch("check") 
     * */
    public function hello($name)
    {
        return "Hello {$name}\n";
    }
}

And now if we execute the following script:

/** @var Dummy */
$dummy2 = new NewNew(new Dummy2);
echo $dummy2->hello("gonzalo");
echo $dummy2->hello("gonzalo1");

we will get

$ php decorators.php
Hello gonzalo

instead of

$ php decorators.php 
Hello gonzalo
Hello gonzalo1

Yes. I know. There is a problem with my implementation. The decorators indeed are public functions too and users can call them. They must be protected functions instead of public ones. I need to play a little bit with reflection in my NewNew class and allow to use protected functions instead of public. I’m working on it but i prefer to show the code “as is” now because is more clear to show the idea, What do you think?

Follow

Get every new post delivered to your Inbox.

Join 949 other followers