Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(web): alternate artifact - es6-bundled Web πŸ“œ #10257

Merged
merged 10 commits into from Jan 8, 2024

Conversation

jahorton
Copy link
Contributor

@jahorton jahorton commented Dec 14, 2023

KeymanWeb's main artifact may now be built targeting ES5 (though needing polyfills) or ES6 (without), the latter of which gives a pretty significant filesize savings.

app/webview will follow with its own set of changes, as I ran into an interesting complication there worth investigating. It's also important to avoid accidentally forcing use of a ES6 artifact for all devices before we get the ES5/ES6 selection code ready for the Android app.

First commit results

New

  ../../../build/app/browser/temp/keymanweb.js ──────────────────────────────────────── 411.5kb ─ 100.0%

Contrast with the feature-branch's current size:

Old

❌ Oh dear! keymanweb.js is 71,830 bytes (17%) larger than 17.0.229, now 485,221 bytes

Second commit results

New

  build/lib/temp/index.js ─────────────────────────── 65.6kb ─ 100.0%

Contrast with the feature-branch's current lm-worker size:

Old

   build/lib/worker-main.mjs ─────────────────────────── 77.3kb ─ 100.0%

Also keep in mind: for a top-level es6 target, we should be able to wholesale drop the polyfills that bloats it to this size in main Web:

Old

   ../../../../common/web/lm-worker/build/lib/worker-main.wrapped.min.js ───────────────── 91.6kb ─ 19.3%

Of note: again, so far these scripts are not connected to the full Web toolchain. They do give us useful information on how many bytes we can expect to 'save', though. I also am not yet building the wrapped version of the es6-bundled worker.

Also of note: these changes do not affect the standard Web build. That said, I haven't yet run any tests or unit tests on either the old es5-oriented artifact or the new, potential es6 artifacts.

Also of note:

  • 16.0.144's minified KeymanWeb weighs in at 384 KB.
  • 411.5 KB - (91.6 - 65.6 = 26 KB) = 385.5 KB.
    • As in, we'll likely end up with minimal growth in comparison to 16.0 stable, let alone 17.0-alpha master!

As of b95051b:

Targeting ES5:

../../../build/app/browser/release/keymanweb.es5.js ──────── 470.7kb

Targeting ES6:

../../../build/app/browser/release/keymanweb.js ──────── 398.1kb

βœ… Excellent! keymanweb.js is 77,512 bytes (15%) smaller than 17.0.230...

Note that this commit's build checks have been performed against the ES6 artifact, not the ES5 one!


@keymanapp-test-bot skip

It's exceedingly unlikely that this would break KMW without it also breaking at least one of the automated tests. There was one break, but it did cause auto-test failure.

@keymanapp-test-bot keymanapp-test-bot bot added the user-test-missing User tests have not yet been defined for the PR label Dec 14, 2023
Copy link
Contributor Author

@jahorton jahorton left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Restoring the comments from the original PR (which got auto-closed when the base branch merged!)

".": {
"es6-bundling": "./src/index.ts",
"default": "./build/obj/index.js"
},
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Many thanks to evanw/esbuild#1250 (comment) for the approach used in this PR.

Leveraging this feature during TypeScript compilation requires TS 5.0: https://www.typescriptlang.org/docs/handbook/release-notes/typescript-5-0.html#customconditions

We're currently using 4.9.5, so we can't leverage that during ES5 builds... not that we've needed to, anyway.

@@ -79,5 +82,6 @@
"src/schemas/*",
"test/"
]
}
},
"sideEffects": false
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Without this specific line, a lot of the package fails to tree-shake out. Notably, all of the precompiled schemas would get included, which would cause major filesize bloat.

evanw/esbuild#1435 (comment)

While the linked comment talks about JS imports, rather than explicitly-TS imports in the manner I've set up here... the same concerns appear to apply.

Perhaps a package used by common/web/types doesn't include the sideEffects package tag, and that's cascading? Just a hunch... at the moment. I do see that there are three external non-dev dependencies that it uses... and one of them has its own dependencies. (None of the three are marked with sideEffects: false, either - but doing this isn't enough.)

I've tried investigating this... but without much luck. All I can say is that something... seems "off" with any attempt to treeshake common/web/types without this package's flag.

The most relevant line of thought I can think of for now: the schema validators are spit out as .mjs files, not TS, making that comment above more relevant. That said, if I locally comment out all Web-ignored exports from common/web/types/src/main.ts, then re-enable the export * as util from './util/util.js', that export doesn't fully tree-shake out, and it doesn't refer to the schemas, so... yeah.

Not sure if it's relevant, but I do see a mild difference with "sideEffects": false for the gesture-recognizer - the subfolder index.ts files - for a common export interface - get tree-shaken out with the flag, but do not when the flag is missing. For the gesture-engine... it makes all of 0.3kb difference.

Does not affect the worker.

Bundling is in a temp-script and not properly connected to our actual build infrastructure.
@jahorton jahorton changed the title feat(web): alternate artifact - es6-bundled Web feat(web): alternate artifact - es6-bundled Web πŸ“œ Dec 18, 2023
@jahorton jahorton changed the base branch from master to change/web/build-bundler-replacement December 18, 2023 03:33
@keymanapp-test-bot keymanapp-test-bot bot removed the user-test-missing User tests have not yet been defined for the PR label Dec 18, 2023
@jahorton jahorton marked this pull request as ready for review December 18, 2023 09:08
@mcdurdin mcdurdin modified the milestones: A17S28, A17S29 Dec 30, 2023
@mcdurdin mcdurdin modified the milestones: A17S29, A17S30 Jan 6, 2024
Base automatically changed from change/web/build-bundler-replacement to master January 8, 2024 08:53
@jahorton jahorton merged commit 8a7394d into master Jan 8, 2024
19 checks passed
@jahorton jahorton deleted the feat/web/es6-target-artifact branch January 8, 2024 08:53
@keyman-server
Copy link
Collaborator

Changes in this pull request will be available for download in Keyman version 17.0.239-alpha

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Development

Successfully merging this pull request may close these issues.

None yet

4 participants