Symfony Plug-In of the week: sfPJS
April 24, 2007 • Published by Francois Zaninotto
In the pursuit for the most cryptic plug-in name, we recently released a plug-in called sfPJSPlugin
. PJS stands for 'PHP JavaScript', and the plug-in offers a new way to include dynamically-generated JavaScript files. For those familiar with the RJS templates in RoR, this is kind of similar, except the code necessary to deal with it is really minimal.
Including a dynamic JavaScript file is great to create unobtrusive behaviours. The main template code contains no JavaScript, all the behaviours are added dynamically in the included file. The same way as you separate content from style with CSS, you separate content from behaviours with JS. The news is, with sfPJS, if the JavaScript behaviours are database or session-dependent, you can include them in a similar way as usial JavaScript files - in one line.
For instance, let's imagine a page displaying "hello, world!" where you would like the text to become a link to an alert box showing the current server time, but only for users with JavaScript support. With sfPJS, this is how you would do it:
<span id="hello">Hello, World!</span>
<?php use_helper('PJS') ?>
<?php use_pjs('foo/bar') ?>
The use_pjs()
helper will call a foo/bar
action and render it by using a foo/templates/barSuccess.pjs
template. Note the .pjs
suffix instead of the usual .php
. The .php
templates are traditionally used to render HTML code, the .pjs
templates are used to render JavaScript code.
So the foo/bar
action is a regular symfony action and can access the request, response and other objects in the same way the others action do:
// In modules/foo/actions/actions.class.php
class fooActions extends sfActions
{
public function executeBar()
{
// Do smart things, like for instance
$this->time = time();
}
}
And the barSuccess.pjs
is seen by the client as JavaScript file, except it is executed by the server and has access to all the symfony helpers and the variables defined in the action.
[php]
// In modules/foo/templates/barSuccess.pjs
<?php use_helper('Javascript') ?>
document.getElementById('hello').innerHTML = "<?php echo link_to_function('Hello, World!', 'alert(\''.$time.'\')') ?>";
You could say that there is nothing revolutionary in this, but the use_ujs()
helper does more than just disabling the layout decoration for the template and setting the response mime-type to application/x-javascript
. By internally forwarding to a special action, the helper allows for fine caching and is much easier to use than the usual use_javascript()
helper.
You can read more about this plug-in in its wiki page.
We will try to speak regularly about interesting plug-ins, so make sure you come back to discover the wonderful add-ons that can make your symfony projects easier to code and funnier to develop.
Help the Symfony project!
As with any Open-Source project, contributing code or documentation is the most common way to help, but we also have a wide range of sponsoring opportunities.
Comments are closed.
To ensure that comments stay relevant, they are closed for old posts.
http://trac.symfony-project.com/trac/wiki/sfUJSPlugin
Also, from the intro it seems like javascript is not mix with HTML, does that means that the tag use_pjs is converted into a <script src=""></script> and in the <head> section?
Or, to put it in a different way, it allows for really unobtrusive scripting with an obtrusive (yet very practical) approach.
And yes, the use_pjs() call inserts a <script> tag directly in the page header, bearing a reference to a symfony action.