document-policy
document-policy copied to clipboard
Allowing cases where document.write is "ok"
Ok ok, hear me out.
I'm assuming we're allowing developers to block document.write because injecting into the browser's streaming parser is a slow path, and can break things like look-ahead parsing.
https://jakearchibald.com/2016/fun-hacks-faster-content/ - here I use document.write in an about:blank iframe to hook into the streaming parser, but I'm pretty sure it doesn't negatively impact the parent page.
Maybe document.write should be allowed if document.open() is called either explicitly or implicitly during the life of the document. In spec terms, I think this means document.write should be allowed if the document open steps have run for this document.
Perhaps it might be simpler in cases like this to just allow the document-write policy on the relevant origin.
I came here to file this issue, but I'd like to go further. Probably the most problematic aspect is the ability to document.write(<script src=script.js>)... which is parser-blocking and thus blocks the main thread on the fetch of script.js, much like sync XHR. https://wpt.fyi/results/html/webappapis/dynamic-markup-insertion/document-write/script_007.html is a simple demonstration of this.
https://developers.google.com/web/updates/2016/08/removing-document-write describes an intervention of parser-blocking scripts when a lot of conditions are met.
Should we have a policy for only the parser-blocking behavior of document.write?
That's what I was trying to define with:
Maybe
document.writeshould be allowed ifdocument.open()is called either explicitly or implicitly during the life of the document. In spec terms, I think this meansdocument.writeshould be allowed if the document open steps have run for this document.
@jakearchibald I see, glad to hear you were also shooting for the same thing!
Trying to figure out what the most surgical restriction of bad document.write behavior would be I came across sync-script which is a policy for parser-blocking scripts.
If that policy also applies to document.write-added scripts, which I presume it does, then are there any remaining performance issues with document.write?
and thus blocks the main thread on the fetch of script.js, much like sync XHR
I made a mistake here, these scripts block the parser, but the document.write call returns before the script is fetched and timers still run, so it's not blocking the main thread, but is blocking important events. (Demo: https://software.hixie.ch/utilities/js/live-dom-viewer/saved/6940)
@clelland, looking at https://github.com/w3c/webappsec-feature-policy/blob/master/policies/document-write.md, I wonder if some of that isn't more about sync-script than document-write. It says:
anti-pattern, parser-blocking JavaScript API
However, is the parser-blocking behavior not covered by sync-script? Is there a problem with document.write in addition to that?
Isn't one of the pros of Feature-Policy so that browsers can not even bother loading chunks of their engine when they see features aren't needed? And hence speed up performance of sites they know aren't using certain features.
This feels like that would defeat that, given engines would need to load it anyway as a call to document.open could still occur at any time.
I think it would be a way better idea to investigate solutions to the use cases of document.write and create a new API that solves them instead of weakening Feature-Policy.
Isn't one of the pros of
Feature-Policyso that browsers can not even bother loading chunks of their engine when they see features aren't needed?
I don't know if that's the case here.
I think it would be a way better idea to investigate solutions to the use cases of
document.writeand create a new API that solves them instead of weakeningFeature-Policy.
That's reasonable, but the new thing should be in place before the deprecation of the old thing.
I don't know if that's the case here.
I can't imagine much by itself (although there seems to be interest in getting rid of it), however combined with other policies (e.g. sync-script/sync-xhr) I can imagine whole parts of the HTML parsing algorithm might be able to be turned off.
but the new thing should be in place before the deprecation of the old thing.
It's not clear to me if document.write is deprecated proper or not, nevertheless Feature-Policy is an opt-in mechanism, if you want to use document.write just don't include document-write 'none' in your Feature-Policy (or specify the domains allowed).
Basically what document.write does is to add text to the input stream of the parser just as if it had arrived on the network (and been decoded) so knowing it won't be called unfortunately wouldn't allow much simplification.
Given enough knowledge of unreachable code it's possible certain fast paths could be enabled, but I don't know that anyone has given this much thought.