Creating HTML: PHP server-side vs. jQuery client-side

If the HTML generated is identical to page HTML you may be able to leverage your existing templating code to generate the same HTML with less code duplication.

Otherwise, JSON is typically more common as it tends to be more compact and it allows you to create nodes and assign non-HTML properties like event handlers to them as you go.

If you create your new nodes by creating an HTML string, however, you have to use HTML-encoding to ensure any <, & or quotes are escaped correctly. There's no built-in function to do this in JavaScript like htmlspecialchars in PHP; it's pretty trivial to write one, but no-one seems to bother. The result is jQuery apps that are full of client-side cross-site-scripting security holes, just as we were starting to make some progress of fixing the server-side XSS stuff.


Why to generate the HTML in PHP:

  • JavaScript should define the behaviour, not the content.
  • Creating in JavaScript requires more markup (multi-line strings aren't as easy as in PHP).
  • It's harder to maintain if your HTML is generated in several places (PHP & JS).
  • You could use jQuery's DOM manipulation functions to create your HTML, but you're shooting yourself in the leg on the long run.
  • It's faster to create the HTML at the server than on the browser (in computational sense).
  • Looping is easier with PHP – it's easy to generate table markup.
  • You retain some kind of combatibility if the user has JavaScript disabled if you output the markup on page load.

Why to generate the HTML in jQuery:

  • You'd save some bandwidth.
  • Binding events might be simpler.

So, I'm in favour of the first option, generating the HTML in PHP.


Visual comparison of the two methods, creating a simple table.  

Option 1, using PHP:

// PHP

$html = '<table>';    
foreach($data as $row) {
    $html .= '<tr>';
    $html .= '<td><a href="#" class="button">Click!</a></td>';
    $html .= '<td>'.$row['id'].'</td>';
    $html .= '<td>'.$row['name'].'</td>';
    $html .= '</tr>';
}
$html .= '</table>'; 
echo $html;
?>

// jQuery

$('#container').load('handler.php', function() {
    $('#container a.button').click(function() {
        // Do something
    });
});

 

Option 2, using jQuery:

// PHP

echo json_encode($data);

// jQuery

$.ajax({
    url: 'handler.php',
    dataType: 'json',
    success: function(data) {
        var table = $('<table />');

        var len = data.length;
        for(var i = 0; i < len; i++) {
            var row = $('<tr />');
            var a = $('<a />').attr('href', '#').addClass('button');

            row.append($('<td />').append(a));
            row.append($('<td />').html(data[i].id);
            row.append($('<td />').html(data[i].name);

            table.append(row);
        }

        table.find('.button').click(function() {
            // Do something
        });

        $('#container').html(table);
    }
});

From a design / ease of coding / beauty point of view, I'd definitely say go with the PHP approach.