krux / postscribe

Asynchronously write javascript, even with document.write.
MIT License
986 stars 157 forks source link

Postscribe fails to catch errors in ad code, subsequent calls fail #15

Closed hcarvalhoalves closed 11 years ago

hcarvalhoalves commented 11 years ago

Please check this fiddle out: http://jsfiddle.net/RAmRg/3/

The issue I'm having is that my ad server sends some ads that thrown an error (more specifically, Unsafe JavaScript attempt to access frame with URL). Postscribe manages to insert the ad on the DOM. After that, all subsequent postscribe calls on the same page fail.

hcarvalhoalves commented 11 years ago

Updated fiddle using latest postscribe version: http://jsfiddle.net/RAmRg/3/

fricto commented 11 years ago

We just implemented this on our site and we are seeing this issue pretty regularly. It's very common for the ads to come with this kind of error, especially rich media banners. Thank you for identifying it.

hcarvalhoalves commented 11 years ago

@fricto Do you have a sample page where the error occurs? I would like to try and debug it. Also, did you found any workaround?

dbrans commented 11 years ago

@hcarvalhoalves, can you explain where you got to in debugging http://jsfiddle.net/RAmRg/3/ ? Perhaps chat or skype would work better. I'm skype:dbrans or gchat: dbrans@gmail.com

hcarvalhoalves commented 11 years ago

@dbrans, the behavior I'm seeing on Webkit (Chrome/Safari):

  1. The first postscribe call in renderAds(); throws an error at https://github.com/krux/postscribe/blob/master/postscribe.js#L427
  2. The error is caught at https://github.com/krux/postscribe/blob/master/postscribe.js#L394 and the error handler is called, successfully logging the error to the console: 'null' is not an object (evaluating 'cursor.parentNode')
  3. At some point (can't figure when), 3rd party ad code attempts to access document.cookie from the parent frame, or do some other kind of illegal operation, and the browser throws the following error, which is not caught by postscribe: Unsafe JavaScript attempt to access frame with URL http://jsfiddle.net/RAmRg/4/ from frame with URL http://ads.dqna.net/banners/images/common/AdDisp.php?bannerid=5931&zoneid=869&sid=67&filename=Netshoes-brazil/300by250Netshoes-brazil_Default_flash2521_07Feb.swf&template_id=22&aid=9&width=300&height=250&tm=30&vzimid=5137d35a0cb594706119451NR&param=s_uol,tcc,tnrg-dcvzr-268828598_,par,. Domains, protocols and ports must match.
  4. After that, I'm not sure what goes on anymore. The next call to postscribe on renderAds() never gets called.

I tried reaching you on GTalk. You can ping me when you're online: hcarvalhoalves AT gmail DOT com

dbrans commented 11 years ago

Hi @hcarvalhoalves, On http://jsfiddle.net/RAmRg/4/ (note the '4' in the url, I grabbed this url from your last comment). I've tried running several times in Chrome and Safari. I'm not seeing the 'null' in not an object. Is there any reason why you have reversed the order of postscribe #banner and postscribe #banner2 in the js? Banner2 works fine but the banner1 ad loads a couple of remote scripts without showing anything. However, I'm seeing "Postscribe Work" twice, which I would expect. Furthermore, the failure of banner1 to show anything doesn't seem to be related to banner2, as I can remove the postscribe of banner2 and see that banner1 behaves the same (nothing showing up). There may be an issue with the banner1 ad itself.

Postscribe cannot catch / detect script errors in an iframe on the ads.dqna.net domain.

Derek

fricto commented 11 years ago

We appear to be seeing it on all browsers, though I've not personally validated that.

We're using this library with backbone's router and our own ajax page loader logic to handle every page load after the first, so everything works like a normal page load on your first page view, and then, once you click a link, we load the page using ajax calls, passing the ads and some other javascript through this library. We're seeing abut a 50% failure rate on the banner ad at the top of the page, and we suspect it's this issue, because we pretty regularly see the 'unsafe javascript' errors. Looking at the ad payload, it appears that it's just not returning the javascript we get back or any of the stuff you'd get from executing it, but you do get back the html comments and the

The only workaround we've come up with so far is to write a callback that grabs the contents of the

hcarvalhoalves commented 11 years ago

@dbrans It might be the case my adserver is serving different ads for you. I had inverted the order on the banners because that's the order it loads on my site, but it fails the same way if I reverse it (one ad loads, the second postscribe inserts nothing in the DOM).

Here's the fiddle and screenshots to make sure we're seeing the same ads:

http://jsfiddle.net/RAmRg/4/

Result: Captura de Tela 2013-03-07 a s 12 34 39

Error thrown: Captura de Tela 2013-03-07 a s 12 34 52

Inverting the order leads to the same error:

http://jsfiddle.net/RAmRg/5/

Result: Captura de Tela 2013-03-07 a s 12 35 06

Error thrown: Captura de Tela 2013-03-07 a s 12 35 17

This is on Safari 6, and I see the same result on Chrome 25.

Postscribe cannot catch / detect script errors in an iframe on the ads.dqna.net domain.

Right, I get that. The error is thrown from inside the iframe, postscribe doesn't evaluate scripts inside the iframe. Usually uncaught exceptions inside the iframe shouldn't halt script execution on the parent frame. So Unsafe javascript attempt shouldn't be the problem here.

The only thing left is the error being thrown (and handled) at https://github.com/krux/postscribe/blob/master/postscribe.js#L427:

'null' is not an object (evaluating 'cursor.parentNode')

I'm not sure about the magic going on postscribe, but it's my understanding cursor can't ever be null since it's the DOM element where you inject the ad tag. I'm curious as to why you're not seeing this error on the console.

dimatter commented 11 years ago

Have the same bug in iOS v 6.1 Safari

hcarvalhoalves commented 11 years ago

This bug seems to be a dupe of #11

dbrans commented 11 years ago

@hcarvalhoalves, would you be able to capture the response from the ad server and put it in a static js file? We should be able to reproduce this with an empty cookie jar. Once I can see it I can fix it. http://plnkr.co/edit/ is good for examples with static files, btw.

11 is an indication of a problem. It should not be ignored with an if statement.

7rains commented 11 years ago

@dbrans

I'm seeing this issue as well. Hopefully this contains what you need. I apologize if it does not. http://plnkr.co/edit/YKZnbCWjK4ZDN9Ywj6qH

dbrans commented 11 years ago

Hi @7rains, when I try to preview that plnkr it does not work. I think you might be missing an index.html where you write the ad call with postscribe.

7rains commented 11 years ago

Hi @dbrans. Sorry about that. This should be better.

http://plnkr.co/YKZnbCWjK4ZDN9Ywj6qH

hcarvalhoalves commented 11 years ago

Thanks for the reproduction @7rains . That's exactly the same issue. Here's what happens when you try to insert two ads:

http://plnkr.co/edit/CJcWlBJIBLlJhEQbkdWo?p=preview

It inserts the first ad, throws an exception, next calls fail.

dbrans commented 11 years ago

Thanks, @7rains, that reproduces the issue. I see the error and postscribe does not finish. I'll get a fix out this weekend.

7rains commented 11 years ago

Thanks @dbrans!

dbrans commented 11 years ago

16 fixes the example @7rains produced. Here is a plnkr with the updated postscribe.js:

http://plnkr.co/edit/UcEUisMN0a4QZp546Iul

The error no longer happens. Let me know if there is still an issue here. I'm closing for now.

hcarvalhoalves commented 11 years ago

Thank you @dbrans . I'll test with my own ad code but this seems to fix the issue.