61

How do i pass jinja2 data into javascript. I have a Flask REST url as /logs/<test_case_name> I am trying use .getJSON() to query the above URL and hence would want to pass the jinja2 data which has the testcasename to .getJSON function.

sample code:

<script type="text/javascript">
  alert({{name}});
</script>

It doesn't work. Any suggestions please?

3
  • 3
    {{ name|safe }} should work Commented Feb 7, 2014 at 11:12
  • @JakobBowyer - it dint work :(
    – deeshank
    Commented Feb 7, 2014 at 11:57
  • 2
    its generally a bad idea to mix template language with javascript. An alternative would be to use html as a proxy - store the name in an element like so <meta id="my-data" data-name="{{name}}" data-other="{{other}}">, then in the javascript do djangoData = $('#my-data').data();
    – Rich Tier
    Commented Feb 7, 2014 at 13:01

8 Answers 8

81

other than encapsulating the variable in a string, an alternate is jquery for profit:

its generally a bad idea to mix template language with javascript. An alternative would be to use html as a proxy - store the name in an element like so

<meta id="my-data" data-name="{{name}}" data-other="{{other}}">

then in the javascript do

var djangoData = $('#my-data').data();

this has advantage in:

  • javascript no longer tied to the .html page
  • jquery coerces data implicitly
11
  • Thanks @rikAtee. I followed the same logic.. just that i used normal div instead.
    – deeshank
    Commented Feb 8, 2014 at 17:24
  • It works but, I think that is a very overkill method - your html file will be bloated with data attributes, I think the answer below (ndpk's) is a better approach Commented Mar 21, 2015 at 16:06
  • Niiiice! Now I can totally isolate html from javacript. This will allow me a clean integration with Flask-Assets. Thanks! Commented May 11, 2015 at 13:05
  • 4
    I'm struggling to understand how the html syntax corresponds to the original question. Is data-name an arbitrary string, or does it have to be data-name? Or just start with data-? Where has the other variable come from? Commented Feb 16, 2016 at 11:33
  • 2
    I think it's worth to mention that you can't give any name to variables inside meta tag, so first I've tried <meta id="geodata" test="{{test}}"> and offcause it don't work. So make variables like this <meta id="geodata" data-test="{{test}}">. It's must be clear from answer, but for some reason it wasn't clear for me at first.
    – Alexey
    Commented Sep 3, 2016 at 8:04
80

Try with quotes:

alert("{{name}}");
1
  • 11
    I think this doesn't work if name contains line breaks such as '\n'. It will throws a javascript syntax error. Commented Dec 21, 2016 at 15:38
17

I know this is a kinda old topic, but since it attracts a lot of views I suppose some people are still looking for an answer.

Here's the simplest way to do it:

var name = {{name|tojson}};

It will 'parse' whatever 'name' is and display it correctly: https://sopython.com/canon/93/render-string-in-jinja-to-javascript-variable/

1
  • 4
    Escape secuence for json is equals to javascript but when add a change in json its broken javascript. For better results respect standars: var name = JSON.parse('{{ name | tojson }}');.
    – e-info128
    Commented Mar 8, 2021 at 4:01
8

I just figure I would add the solution I ended up using.

It has a few advantages over the other answers:

  • It is 100% valid javascript at the template level (no editor/lint errors).
  • Does not need any special HTML tag.
  • No dependencies (jquery, or otherwise).
let data = JSON.parse('{{ data | tojson }}');
2
  • 1
    When using with more complex syntax like JSON.parse('{{ url_for(\'foo.bar\', filename = \'foobar.txt\') | tojson }}');, this gives an Uncaught SyntaxError: Unexpected token { in JSON at position 1
    – emilaz
    Commented Jul 8, 2021 at 11:36
  • That might very well be a bug then. My understanding is the filter is a wrapper around json.dumps, not really sure but I doubt anyone implemented a json encoder for this. Commented Jul 9, 2021 at 12:36
5

This is how I did it

My html Element

<!--Proxy Tag for playlist data-->
<meta id="my_playlist_data" data-playlist="{{ playlist }}">

My script element

// use Jquery to get data from proxy Html element
var playlist_data = $('#my_playlist_data').data("playlist");

See .data() documenttation for more

2

you can try alert({{name|safe}});

1
  • 2
    Hi There. Try elaborating or post a comment. Commented May 15, 2021 at 14:17
1

<input type="hidden" name="token_idx" id="token_idx" value='{{token|safe }}'

let token_data = document.getElementById("token_idx").value;

1

Adding my working solution from HTML as I spent a full day hunting for it in case it helps someone.

This html is passed back its prefill data and I could not get access to the variables I needed from that dict in the Jinja2 for loop

render_template('home.html', prefill_data=request.form)

The real key here was this trick to get a variable in as key in string format prefill_data["player{}name".format(n)]

And these curly braces to access value as string "{{ prefill_data["player{}name".format(n)]}}"

{% if nplayer_form is not defined %}
    {% set nplayer_form = 4 %}
{% endif %}   

{% if session['additional_players'] %}
    {% set nplayer_form = nplayer_form + session['additional_players'] %}
{% endif %}


{% for i in range(nplayer_form) %}
    {% set n = i+1 %}

<tr id="Row{{ n }}">
<td>
<label for="player{{ n }}name_input" name="player{{ n }}name_input_label"></label>
<input type="text" name="player{{n}}name" id = "player{{n}}name_input" {% if prefill_data %} value="{{ prefill_data["player{}name".format(n)]}}"{% endif %}/>
</td>

<td>
<label for="player{{n}}strength_id" name="player{{n}}strength"></label>
<select name="player{{n}}strength" id="player{{n}}strength_id"> 
    <option value="1" {% if prefill_data %}{% if ((prefill_data["player{}strength".format(n)]) == "1") %} selected {% endif %}{% endif %}>Beginner</option>
    <option value="2" {% if prefill_data %}{% if ((prefill_data["player{}strength".format(n)]) == "2") %} selected {% endif %}{% endif %}>Intermediate</option>
    <option value="3" {% if prefill_data %}{% if ((prefill_data["player{}strength".format(n)]) == "3") %} selected {% endif %}{% endif %}>Advanced</option>                 
</select>
</td>

<td>
<label for="p{{n}}checkbox_id" name="p{{n}}checkbox_label">
<input type="checkbox" id="p{{n}}checkbox_id" name="p{{n}}checkbox" {% if prefill_data %} {% if (prefill_data["p{}checkbox".format(n)] =="on") %} checked {% endif %} {% endif %} />
</label>
</td>

</tr>

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