Kappers
Kappers

Reputation: 1331

How do I prevent javascript returned from an ajax request from executing when the response is inserted into the DOM?

So, I see so many people wondering how to execute JS code returned via ajax. I wish I had that problem. My JS executes, but I don't want it too!

Using jQuery 1.4.2, I'm making a GET request:

$.ajax({
  url:'/myurl/',
  type:'GET',
  success:function(response){
    $('body').html(response);
  }
});

The response looks something like:

<p>Some content</p> 
<script>alert("hi!");</script>

Whenever the success callback fires and the response is injected into the DOM, the alert code fires! I don't want that to happen. What can I do to prevent this?

Upvotes: 3

Views: 1704

Answers (5)

molicule
molicule

Reputation: 5561

The problem you have is that jQuery strips script tags from the html and creates a document fragment.

To elaborate

var e = $("<div>Hello</div><script>alert('hi')</script>")
e.html(); // will not display script tags as script tags are now in a document fragment
$("body").append(e); // will execute the script tags in the fragment

See John Resig's explanation and another forum post on this topic.

So, what you can do is

var e = $("<div>Hello</div><script>alert('hi')</script>")
e.filter("script").each(function(){this.text='';});

That would basically make all the scripts empty and now you can

$("body").append(e);

See this post for the fragment creating routine.

Upvotes: 0

Ajaxe
Ajaxe

Reputation: 647

did you try returning function() snippets like
<script>
function Hello(){
alert('Hello');
}
</script>

This way the your JS doesn't execute right away but can be called later when required. But, again it depends what you actually want to do.

Upvotes: 1

kennebec
kennebec

Reputation: 104810

 $('body').html(response.replace(/(<script)[^\>]*/g,'$1 src="emptyfile.js"'));

where emptyfile.js exists but has no content.

Upvotes: 0

BrunoLM
BrunoLM

Reputation: 100361

If you can't modify the response, try to "replace" <script> tags:

"<script>alert('hi');</script>".replace(/<(\/?script)/gi, "&lt;$1");

This should escape the tags, making they appear as plain text instead of executing.

Related links

Upvotes: 1

Sid_M
Sid_M

Reputation: 399

Depends. Do you need the JavaScript, or can you just get rid of it? If you don't need it at all, you could do something like

response = response.replace(/<script.*?<\/script>/gi, "");

However, if you need it, you're going to need to figure out how to kill just the function call(s) that you don't want. Using your example of an alert:

response = response.replace(/alert\(.*?\)/gi, "alert");

By getting rid of the trailing parens, and whatever they contain, you stop the function call from happening. Obviously, what you'll need in your regex will depend on the actual code that's causing the problem.

Upvotes: 0

Related Questions