The hints of XSS game's level2 say that

Entering a tag on this level will not work. Try an element with a JavaScript attribute instead.

When entering


the resulting HTML after submiting is

<td valign="top" class="message-container"> 
  <div class="shim"></div>
   <b>You</b><span class="date">Wed May 18 2016 </span>

and the XSS is not triggered. If I replace it with

post-content=<img src='foobar' onerror='alert("xss")'>

it fires!

I've copied the whole HTML to a separate file on my computer, run the first case and the script fired!

So what is different from case 1 to case 2? Should case 1 work too?

1 Answer 1


The relevant code for the HTML generation is the following:

for (var i=0; i<posts.length; i++) {
  var html = '<table class="message"> <tr> <td valign=top> '
    + '<img src="/static/level2_icon.png"> </td> <td valign=top '
    + ' class="message-container"> <div class="shim"></div>';

  html += '<b>You</b>';
  html += '<span class="date">' + new Date(posts[i].date) + '</span>';
  html += "<blockquote>" + posts[i].message + "</blockquote";
  html += "</td></tr></table>"
  containerEl.innerHTML += html;

As we can see, the HTML is being set in the DOM via innerHTML, which means that the script tag will not be executed, because per-specification, innerHTML does not execute scripts. More on why can be found on the Stack Overflow question script tag create with innerHTML of a div doesn't work.

I've copied the whole html to a separate file on my computer, run the first case and the script fired!

Presumably you copied the resulting HTML which means it was not created by innerHTML, but permanently in the HTML source, so it ran.

  • I can't figure out why </blockquote isn't closed but still appears as is.
    – Xavier59
    May 18, 2016 at 19:07
  • 2
    @Xavier59 Auto-magical error handling. May 18, 2016 at 19:14

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .