Output Filters in Zend_View

A feature of Zend Framework MVC that isn’t currently very well documented is output filters. They’re mentioned in passing in the Zend_View documentation, but not reviewed in detail anywhere in the Reference Guide as of version 1.5.2. I was curious enough about how to implement markup minification that I decided to trace through the Zend_View source code in attempt to discern how output filters actually worked. As it turns out, it’s actually pretty simple.

First, you need to get a reference to the current Zend_View instance. If you’re using the Zend_Layout MVC integration, you can get this by calling $this->_helper->layout->getLayoutInstance within your Zend_Controller_Action class to get the current Zend_Layout instance and then getView on that to get your Zend_View instance. Otherwise, the Zend_View instance is available via the view property of Zend_Controller_Action instance.

Next, call addFilterPath or setFilterPath on your Zend_View instance from your Zend_Controller_Action class. Pass in a path to the directory to contain your output filter classes and a naming prefix that all of your output filter classes will use. I’m not sure why the class prefix defaults to “Zend_View_Filter_” since no such classes exist. In my opinion, it would have made more sense to derive the prefix based on the provided directory path. Anyway, create the directory you’ve specified if it doesn’t already exist and create a new class file within that directory. In my case, I named the directory Vendor/View/Filter, the file Minify.php, and the class contained in the file Vendor_View_Filter_Minify.

Within this class, you must implement at least one method, filter. This method should accept a single parameter, which will be a string containing the view ouput to be filtered, and should return the filtered version of that string. Optionally, if your filter requires access to the related Zend_View instance, you can also declare a setView method that accepts the Zend_View instance as its only parameter and it will automatically be passed in when your output filter class is instantiated. Within setView, you can store the Zend_View instance in an instance property of the output filter class so it can be referred to later in the filter method.

Once you’ve finished your output filter class, you need to explicitly add it to the output filters in use from your Zend_Controller_Action class. You can use addFilter or setFilter for this. Pass in the name of your output filter class without the class prefix. In my case, I passed in “Minify.” At this point, the filter should be used when rendering your page. I poked around in the DOM and Tidy PHP extension documentation, but couldn’t find a feature for markup minification, so I ended up using the PCRE extension to do the job. Below is the final source code for my output filter class.

Vendor/View/Filter/Minify.php

class Vendor_View_Filter_Minify
{
    public function filter($string)
    {
        return preg_replace(
            array('/>\s+/', '/\s+</', '/[\x0A\x0D]+/'),
            array('>', '<', ' '),
            $string
        );
    }
}

Vendor/Controller.php

class Vendor_Controller extends Zend_Controller_Action
{
    public init()
    {
        $this->_helper->layout->getLayoutInstance()->getView()
            ->addFilterPath('Vendor/View/Filter', 'Vendor_View_Filter_')
            ->addFilter('Minify');
    }
}

5 Comments

  1. … all posts in Development” rel=”category tag”>Development Matthew Turland has written up a new tutorial explaining something that’s “currently very well documented” in the Zend Framewor…

  2. matsu says:

    Thank you for the great artcle.
    This is what I’m looking for!

  3. …t:pageTracker._trackPageview(‘/outbound/article/http://ishouldbecoding.com/’);”>Matthew Turland Minify Filter for Zend Framework i decided to implement the

  4. Steve Clay says:

    FYI, Minify_HTML is a simple class for minifying markup fragments or pages (and can run callbacks on embedded CSS/Javascript).

  5. I found this page while looking into making my own CSS/JS minifier. I modified your preg so it will minify even more stuff:

    // Characters we want to look for so we can replace them
    $search = array(
    ‘|(/*.*?*/)|’, // Comment tags
    ‘/>s+/’, ‘/s+</’, // spaces before/after > or
    ‘/[x0Ax0Dx20x09]+/’, // returns, multiple spaces/tabs
    ‘/s?;s?/’, // spaces before/after ;
    ‘/s?{s?/’, // spaces before/after {
    ‘/s?}s?/’ // spaces before/after }
    );

    // Replacements for aforementioned characters
    $replace = array(”, ‘>’, ‘<‘, ‘="" ‘,="" ‘;’,="" ‘{‘,="" ‘}’);="" performed="" minification="" (queue="" mad="" scientist="" laugh)="" $minified="preg_replace($search," $replace,="" $buffer);="">