-
Notifications
You must be signed in to change notification settings - Fork 17.4k
Minify the startup snapshot script with terser #17926
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That's pretty amazing! Does it have a similar reduction in the app size?
|
Looks like the macOS failure was a flake. Restarting... |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
😍 Neat! Awesome find.
One question: I see that we aren't generated sourcemaps for the minified code. Does this result in mangled stacktraces? An inline sourcemap would defeat the purpose of the minification I'm sure... but maybe one saved in a separate file wouldn't be loaded unless you actually needed it... ?
I've actually wondered if we could get away with not shipping source at all by default - relying on the snapshot for distribution of core and bundled packages. Maybe bundling it separately and downloading it on demand so that people could debug. It would really slim down our app download. It's probably not worth it though 🤔
| process.stdout.write('Minifying startup script') | ||
| const minification = terser.minify(snapshotScript, { | ||
| keep_classnames: true, | ||
| compress: {keep_fargs: true, keep_infinity: true} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just curious - did classname mangling break something?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, I think we have some code that uses ‘constructor.name’. I was seeing errors in the GitHub package; something about repository state transitions...
I didn’t look into it too deeply though.
|
Yeah, great points about stack traces and source maps. We’d need to do that before merging this. Hopefully it won’t negate the memory savings. I think the only reason we include the source in the bundle is so you can run Atom in dev mode for debugging without having the source checked out. Not sure how many people do that though. |
|
Actually, I don't think we need to do anything for stack traces. Here's an example error that I produced by manually breaking my editor from the dev tools: Since property names are not mangled by default, and I've disabled mangling of class names, everything is just as clear as before. Even before this change, the line numbers weren't really useful because they were referring to the concatenated |
|
One other drawback: the dev tools becomes unresponsive for about 10 seconds if you try to open the |
|
Alright, CI passed after a rebuild: https://github.visualstudio.com/Atom/_build/results?buildId=5607&view=logs |
It looks like it does reduce the size of
I agree. The source code is not very useful anyway in the form that we ship it. If people really want to debug Atom's bundled code, they pretty much need to clone and build Atom anyway. I'm inclined to attack this in a separate PR, but I do think it's worth doing. |

Background
I was just looking at a heap snapshot in Atom and I noticed something striking - over a third of the memory allocated on V8's heap is due to a single
scriptobject: Atom's concatenated startup script.In particular, the script retains a reference to its source code as a string, which consumes around 45MB of RAM:
In addition, the script maintains an array of
line ends, which I assume V8 uses for computing stack traces. This consumes almost 3MB.Proposed Change
In this PR, I minify the startup script that
electron-linkgenerates usingterser(a fork of uglify that works with es6).Results
When I compute a heap snapshot after minification, the startup script's
sourcenow consumes only 16MB on the heap, and itsline endsno longer shows up in the snapshot (there are no line endings any more).To get a sense of the overall impact, I rebuilt
Atom Devwith this change and ran it simultaneously with the most recentAtom Beta. In each case, I opened one file in theatom/atomrepo. When all is said and done, it looks like this reduces our memory consumption by 45 MB per window, and the same amount in the main process!Drawbacks
The minification step does take some time. It adds 10 - 20 seconds to the build.