I am rendering a .js.erb
file within my rails app. Within this file, I'm updating the options for a select box.
The most important thing is that I am doing this in a XSS Safe manner. Given the solution of this SO Post, which references OWASP DOM based XSS Prevention Cheat Sheet, I am updating the select box options the following way:
Attempt 1
// app/views/blogs/blogs_select_listing.js.erb
// remove all options
$('#blog_select_box').children().remove();
// iterate through @blogs collection, append each blog item as an option to select box
<% @blogs.each do |blog| %>
var opt = document.createElement("option");
opt.setAttribute("value", "<%= blog.id %>");
opt.textContent = "<%= blog.name %>";
$('#blog_select_box').append(opt);
<% end %>
- Issue: the display text of
blog.name
is being html encoded. So for example, the text of "Johnson & Johnson" is instead being displayed as: "Johnson&
Johnson". Other special characters like apostrophes will have the same display issue.
Attempt 2
I am aware of the rails method html_safe
, so I tried that: I updated "<%= blog.name %>";
to "<%= blog.name.html_safe %>";
.
- Issue: When I test for XSS via having
blog.name
be something likealert("Gotcha");
, it breaks: The options are not updated at all. Ultimately it seems that the issue is that usinghtml_safe
in this context, the app doesn't know how to handle double quotes.
Atempt 3
This seems to work. It updates the options, the display text works, and the option with display text alert("gotcha");
simply displays as text and it doesn't execute as code:
// app/views/blogs/blogs_select_listing.js.erb
// remove all options
$('#blog_select_box').children().remove();
// iterate through @blogs collection, append each blog item as an option to select box
$('#blog_select_box')
.html("<%= j options_from_collection_for_select(@blogs, :id, :name) %>");
- Issue: I'm uncertain if this is safe. I am uncertain because I ran across this article which expresses that
j
, which is an alias forescape_javascript
is unsafe.
It is currently unclear how I can update select options from a .js.erb
template which is both XSS safe and properly displays the text.