tags:

views:

221

answers:

5

I'm starting to understand the importance of templating in PHP. I'm using PHP itself as a template engine to avoid learning any new language. I'm still not clear on one thing tho, although I have an idea about it. I would like to know what the experts do.

Should I create a full page template, with all tables, forms and everything else (including header and footer), or should I put all of my tables, forms, etc in their own file and then add them to the template as needed.

Here's a small example to clear things up...

Should I

a) create one page with all the tables, forms, and other elements in it and use that as a final product

// Set all the information
$template->title = $username;
$template->user_info = get_user($user_id);
$template->articles = get_articles($user_id);
$template->ads = random_ad($user_info);

// Load the template with everything already in it
$template->load('user_page.tpl')
$template->display();

OR

b) create every table, form, related block element in its own file and then use those to create a final product

// set the title and load the header template
$header['title'] = $username;
$template->load('header.tpl', $header);

// get the user info as an array and load into user profile template
$user_info = get_user($user_id);
$template->load('user_profile.tpl');

// load the new article form
$template->load('new_article_form.tpl');

// get the articles as an array of info and load into user articles template
$articles = get_articles($user_id);
$template->load('user_articles.tpl', $articles);

// get a random ad based on user info
$ads = random_ad($user_info);
$template->load('advertisements.tpl');

// load the footer template and display final page
$template->load('footer.php');
$template->display();

Where every file loaded contains a small portion of what needs to be displayed on the final page.

Because of the Dont Repeat Yourself technique, I would think B, but i would like to know which and why

A: 

There is no good or bad solution. There are techniques and guidelines but in time you will learn what approach is better than others.

Just by looking at it i would say that the second approach allows you to be more flexible and breaks down the page into smaller parts. Smaller might some times mean more manageable.

Also the second solution also allows more than 1 persons working on the page since they will only need to work/change parts of the page and not the whole page.

regards,

andreas
+3  A: 

I would personally say the first approach is best, because it keeps all documents and document fragments semantically complete.

The second approach means that you'll have a <div> in your header.tpl that is closed by a </div> in your footer.tpl (except likely there will be a few tags that applies to). This means if you change your layout, by adding a wrapper div (for example) somewhere, you have to remember to also close it in another file (or, depending on your layout, two or three different files).

It's worse with several different embedded files. Think of how hard it is to debug a site, when one file - that gets included conditionally - has an extra </div>. You get a vague bug report "sometimes the page looks completely messed up, doesn't matter what browser I use" that is very very hard to track down. It's MUCH worse if you're using table-based layouts..

Using the first approach, you can still use the DRY principle. You load the template into a variable. eg:

$userVars['name'] = $currentUser->name;
$templateVars['userinfo'] = $template->load('userinfo.php', $userVars);

...
$template->display('template.tpl', $templateVars);

You can continually nest documents that way. There are many benefits:

  • Each file is semantically complete HTML - all tags that are opened, are also closed in the same document. It's easy to edit one part of the layout without breaking (possibly unknowningly) anything else.
  • It's each to cache the output of certain templates, and re-use them
  • It's easy to apply AJAX to the site. For example, you have a stats.tpl template rendering inside a <div id="stats"> on the first page load. You also have a view that just renders the stats.tpl template by itself, and then use jquery to do $('#stats').load('/ajaxstats.php'), which refreshes that div but without repeating code at all.
gregmac
A: 

As gregmac suggested, the first solution is probably preferable. Having said that, I would also suggest to have a look at the various PHP frameworks available, most of which implement templates using various techniques.

Have a look at this list for a start. You may also want to take a look at some stand-alone template engines, such as Smarty, in order to get some ideas or to avoid implementing your own engine.

Anax
+2  A: 

Template inheritance for structures common to every template (e.g. layout; header/footer), and template embedding (i.e. including) for reusable bits (e.g. forms).

With approach A and without inheritance, you'd be either including common layout elements (which is IMHO ugly), or duplicating entire layout in every template (which is even worse). And plain approach B would create massive amounts of tiny template bits for everything, which may reduce maintainability.

And for that, I really recommend using real, dedicated templating engine instead of plain PHP. They make life easier (inheritance is one thing; another - variable auto-escaping).

PiotrLegnica
A: 

template inheritance would probably make the cleanest code. you can do this now in straight php using PHP Template Inheritance

arshaw