Open petrcermak opened 9 years ago
Hmmm... thats not a bad idea. @anniesullie @qyearsley for thoughts.
In the #1714 case, the error makes me think that the vulcanized result we're producing isn't itself in strict mode? Is that intentional or accidnetal I wonder?
Yeah, we should definitely do this. Seems like it should be possible to do with modifications to run_dev_server_tests.py, just not sure how to do it in a general way instead of a hacked on way.
I like the idea of starting simple and just opening the vulcanized file and seeing if we have window errors.
Running the tests on the vulcanized data I think might be tough.
I was also quite surprised to learn that the vulcanized file is not in strict mode (or at least not in Chrome's "opinion").
I had a quick look at trace_viewer_full.html and the problem is that the vulcanized file contains a single element, which is a concatenation of all Trace Viewer scripts (including third_party code), some of which are in non-strict mode. The first concatenated script (Polymer) turns out to be non-strict, so the whole concatenation is considered to be non-strict by the browser (because 'use strict'; is ignored unless it's the first statement in the concatenated script):
<script>
/* Polymer code (non-strict) */
...
'use strict'; // Ignored because it's not the first statement in the <script>.
/* Trace Viewer module */
'use strict'; // Ignored because it's not the first statement in the <script>.
/* another Trace Viewer module */
...
</script>
Apparently, concatenation of non-strict and strict scripts is a well-known issue (https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Strict_mode#Strict_mode_for_scripts).
If we want to address this (which I think we should because strict and non-strict mode have different semantics), then two relatively straightforward solutions come to my mind:
Option 1. Separate the concatenated script into non-strict and strict elements:
<script>
/* Polymer code (non-strict) */
...
</script>
<script>
'use strict';
/* Trace Viewer module */
'use strict'; // Ignored because it's not the first statement in the <script>.
/* another Trace Viewer module */
...
</script>
This might not be possible if some strict and non-strict scripts are interleaved and we cannot reorder them for some reason.
Option 2. Do not concatenate scripts at all.
<script>
/* Polymer code (non-strict) */
</script>
...
<script>
'use strict';
/* Trace Viewer module */
</script>
<script>
'use strict';
/* another Trace Viewer module */
</script>
...
This should be quite simple to do.
The only question is whether this could have any impact on performance. I discussed this with some V8 people on our team and splitting the script might actually improve the loading performance because the browser might be able to better interleave frame rendering and script parsing.
Regarding the vulcanized file size, the impact of doing this should be relatively small: The whole file has 1,665,160 characters (~1.6 MiB). It contains 424 occurrences of 'use strict';. Assuming all of them correspond to scripts and there is an equal number of third_party scripts (unlikely), we would be looking at approximately 20,000 extra characters (~19.5 KiB) for the extra and tags.
@nedn since he's done some tests of vulcanization + performance
Yeah, I also fixed a few bug when sending out https://codereview.chromium.org/1417883005/ for review. We should add: "trace-viewer test with vulcanize + vinn test with vulcanize"
For the issue of 'use strict', how about we tell py_vulcanize to add 'use strict' as the first statement of < script> block? I would prefer we be able to keep the single < script> tag since that would enable further minification down the road.
It's probably worth trying, but it might break and/or slightly change the behavior of some third-party dependencies.
As a fallback, if the third-party dep once are problem with 'use strict', I think we can add some special bit so that py_vulcanize be smarter about adding them.
<script src='third_party.js' inline="false">
Lemme back up and deal witih fundamentals... we have some scripts that aren't strict mode. So we can't just force them to strict mode. That would be a breaking change, too.
Fortunately, strictness is a function level thing. So, one thing you can do is put each file in (function() { ... })()
blocks. That'd probably create a lot of useless function scoping though, so we may want to group files together when they're all strict mode. Shrug.
It turns out that some bugs only occur once Trace Viewer is vulcanized (e.g. #1714). Therefore, I think that it would be a good idea to have some instrumentation tests for vulcanized Trace Viewer as well. The bare minimum would be a test that checks that the vulcanized HTML file loads in a browser without any exceptions.
@natduca, @dj2: WDYT?