PHP templates:
Smarter sans Smarty

At one time, I got all up and excited about Smarty, so I rewrote a lot of PHP code to use Smarty templates.

Of course, this was only after I had already rewritten this code to abuse object orientation in the worst of possible ways. To imagine the extend of this horridness, imagine a class for each screen, all derived from the same Screen superclass. Each class had to implement the display() function, which contained, verbatim, all the HTML tag-soup to throw upback at the browser. I don't think anyone will be surprised when I say that throwing Smarty in the soupmix didn't make it taste that much better.

Of course, learning, extending, working around and getting increasingly frustrated with Smarty was fun, but as much as it was fun, it was also a complete and utter waste of time.

Why? What's wrong with Smarty?

There's nothing wrong with Smarty. It's very well written, works without a glitch and serves its purpose just fine. PHP itself, however, serves this purpose even better. Because, in the end, PHP still is a templating language. PHP is also a very complete templating system. I mean, it has to be if it even lets you invent your own templating language. But, just that you can doesn't mean that you should.

The smarts of Smarty

Easy variable substitution

Most of the time in a templating language is spent spitting out variables.

Variable substitution in Smarty


  

Hi {$person.name},

]]>

Variable substitution in PHP


  

Hi ,

]]>

If $person['name'] equals Rowan, both examples will generate the following HTML:


  

Hi Rowan,

]]>

Which of these looks better is mostly a matter of taste. Related to taste, it should be mentioned that the PHP example could be abbreviated to the following if you have enable_short_tags enabled (which I wouldn't recommend for the same reasons as why I don't like the syntax of most templating languages):


  

Hi ,

]]>

The question of which one of the two works better can be answered by applying Occam's Razor: why add unnecessary cruft to your process if the same result can be achieved without?

Explicit variable assignments

With template languages such as Smarty, you need to explicitly assign each variable that needs to be available from the template. This is usually tauted as a feature, because it forces you to think before you start throwing data at you presentation templates.

Assigning variables for the use in Smarty is easy.

assign('person', $person);

?>
]]>

But, without Smarty, it's easier still.


]]>

If you really want the kind of strict separation as encouraged by a templating system, it can be achieved much easier without one. Just include() or eval() your templates from within the scope of a function or method and you can exactly define what you want access to. (Somewhere below, I provide a list of PHP frameworks that support view/controller separation without requiring custom syntax.)

Variable modifiers?

So what are variable modifiers? They're some sort of pipe-like notation for a restricted set of functions.

Variable modifiers in Smarty ...


  
  • E-mail addy: {$email|escape:"html"}
  • ]]>

    ... are simply functions in PHP

    
      
  • E-mail addy:
  • ]]>

    You can add variable modifiers by writing a Smarty plugin according to a well-defined plugin interface. But, why bother if you can already add functions to PHP through a well defined function definition interface?

    This Smarty plugin definition is just a cumbersome version ...

    ]]>

    ... of this similarly simple PHP function.

    ]]>

    Traversing arrays

    Traversing arrays in Smarty

    
      

    People list

      {foreach from=$persons item=person}
    1. {$person.name}
    2. {/foreach}
    ]]>

    Traversing arrays in PHP

    
      

    People list

    ]]>

    Advantages of using PHP as a templating language

    Familiar syntax and functions

    No need to learn separate syntax depending on the templating system of the day. Just stick with familiar PHP syntax, or, if you don't know PHP syntax, learn a skill which is actually portable across projects and jobs.

    XML compliant <?php ?> processing instructions

    Thanks to PHP's compliance to XML processing instructions, PHP can be used in any part of the XML toolchain. E.g.: it's easy to process XML code that contains PHP using XSLT or any other XML-PI-aware tool.

    Reasons to still use Smarty and why they're all wrong

    “You can't use PHP for templates, because template designers don't know PHP.”

    wildleaf on Digg refutes this argument neatly:

    So instead of teaching them minor PHP (such as simple loops and how to print out variables with a $ in front of them) you will tell them to put in a specially formatted HTML comment or some sort of ##VARIABLETOPRINT## that they will paste all over the place. How is any templating language any easier than basic template based PHP?

    PHP syntax is pretty simple and consistent and everything related to outputting and formatting stuff can be done with simple functions without having to learn anything about more complicated issues such as object architecture.

    In the same Digg discussion, Joel Hardi takes the argument even further:

    Yeah, all these crappy template languages are a solution looking for a problem, just developers scratching an itch.

    I would love to never have to learn another one, but instead every CMS developer has to invent a half-declarative, half-functional templating language that winds up taking acres of time even for developers to learn—let alone the graphic designers and other folk these templating languages are supposed to be dumbed down for. And your typical HTML-savvy designer would much rather pick up a some inline PHP skills to put on the resume; than learn some obscure templating pseudocode.

    Indeed. If you, as a designer, were to add a skill to your resume, which would you rather add: (Obscure) templating language X or experience with PHP?

    Separation of the business logic and presentation logic

    Yeah, presentation logic. Some templating languages have you define blocks, the behaviour of which you then still have to define in your code.

    The nonsense of this argument is so obvious that it shames me that it took me a lengthy trip through template territory to acknowledge the simple truth: there is noöne stopping me from putting all presentation-related code in its own little layer, and this is, in fact, what the newer PHP frameworks and template systems do.

    Hans Zaunere's, in A Tale of Three Templates:

    Web pages have become so complex that a certain level of logic is required within HTML, which is underscored by the fact that the external templating engines have this functionality.

    Buzzword compliance

    You really do a need a separate template language because of buzzword compliance? Then I suggest going for a level of buzzword compliance which can only be found in XSLT.

    Proponents and opponents of this approach

    Of course, most of the arguments used here didn't come from me, myself or I.

    Frameworks using pure PHP templates

    Finally, you may want to take a look at my own simple function for applying pure PHP templates.


    Discuss this article on Digg or on reddit.