8
\$\begingroup\$

I have an already rendered template and I want to update it with some JSON data I obtain via AJAX.

The template as it is before rendering looks like this (using jinja2 template engine):

<table>
<thead>
    <th> Time </th>
    <th> Destination </th>
    <th> Bus number </th>
</thead>

<tbody id="table-body">
{% for bus in buses %}
<tr>
    <td> bus[0] </td>
    <td> bus[1] </td>
    <td> bus[2] </td>
</tr>
{% endfor %}
</tbody>
</table>

And I want to send AJAX requests to update the buses var with new values. The way I do it is deleting the tbody content when new data arrives, and rendering everything again with the new data.

function executeQuery() {
    $.ajax({
        method: 'get',
        url: '/data/json',
        data: { bus_id : {{ bus_id }} },
        success: function(data) {
            data = JSON.parse(data);
            $('#table-body').html('');
            for (i in data){
                $('#table-body').append(
                    "<tr>" +
                    "<td>" + data[i][0] + "</td>" +
                    "<td>" + data[i][1] + "</td>" +
                    "<td>" + data[i][2] + "</td>" +
                    "</tr>");
                };
        }
      });

How can I improve this code? (FWIW I'm using Flask)

\$\endgroup\$
6
\$\begingroup\$

If you're using a jQuery collection more than once, make sure to set a variable, this means you don't have to do unnecessary DOM lookups:

 var $table = $('#table-body');

You can probably improve your append code to make it more legible. Personally I prefer utilising the jQuery methods where possible, such as .text().

 data = JSON.parse(data);
 $table.empty(); // empty is more explicit
 // iterate over the data
 data.forEach(function (buses) {
   // create a new table row and append it
   var $row = $('<tr>')
     .appendTo($table);
   // iterate over the buses
   buses.forEach(function (bus) {
     // create the cell, set the text, 
     // and append it to the row
     $('<td>')
       .text(bus)
       .appendTo($row);
   });

 });

Since you're just doing a simple get, you can use jQuery shorthand $.get function:

$.get('/data/json', { bus_id : {{ bus_id }} })
  .success(function (data) {
    // do render
  });
\$\endgroup\$
2
\$\begingroup\$

If you want to keep this basic structure (so not switch to a framework), then you can just store the bus ID on each row, <tr data-bus-id="42"> and later, when you get new data, only replace the contents in the new rows you got.

Furthermore, you could also do change detection, but then I have no idea if that is worth it (you'd have to profile first). All this will make your code way more complicated, so be sure that added performance is worth the overhead.

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.