-
-
Notifications
You must be signed in to change notification settings - Fork 32.3k
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
[core] Ship modern bundle #22814
[core] Ship modern bundle #22814
Conversation
@material-ui/core: parsed: -4.81% 😍, gzip: -5.94% 😍 |
.browserslistrc
Outdated
last 1 safari version | ||
node 14 | ||
|
||
# snapshot of "> 0.5%, last 2 versions, Firefox ESR, not dead, not IE 11" when the last major is released. |
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.
Widening to 0.2%
(which is what create-react-app is using; 0.5 is browserslist default) would include:
- chrome 49
- edge 18
- ios_safari 9.3
Chrome and edge are evergreen so I think we can ignore these versions. Older Chrome versions used to be relevant since it was what google used to crawl sites but they since upgraded and are doing so more often.
Note that safari prior to 12 would need prefixing of gap
and column-gap
in ImageList
. Prior to 10.3 these properties aren't supported at all.
ios_safari cannot be considered evergreen because it's tied to the OS and therefore the device. The devices that support iOS 9 but not iOS 12 are:
- iPod Touch (5th generation)
- iPhone 4S
- iPhone 5
- iPhone 5C
- iPad Mini (1st generation)
- iPad 2
- iPad (3rd generation)
- iPad (4th generation)
- iPad Air
- iPad Pro (12.9-inch 1st generation)
Using https://en.wikipedia.org/wiki/IOS_9#Supported_devices and https://en.wikipedia.org/wiki/IOS_12#Supported_devices
8f3144e
to
9d539bc
Compare
99b022e
to
9ed4ecb
Compare
Only due to missing module concatenation (which depends on the app bundle not library code). Stat size is now at 14.58 kB (down from 15.94 kB) |
9ed4ecb
to
4a1eef2
Compare
Me neither. Breaking imagelist on iOS < 12 was unintentional... |
@mbrookes What do you mean? Only supporting iOS >=13 was intentional. I have seen the following error in development mode coming from the changes (none of the docs pages are working in dev) I haven't figured out why yet. |
Sure but it's not clear whether this is viable. The benefit of dropping iOS < 13 is that we can use PointerEvent as well. |
Does it going to ship ES6+ syntax or later? Want to see that happen |
The The default bundle should have a lot less transpilation as well. What is so specific about ES6 syntax that you'd want to see? |
Cool, thanks |
A second version of the components is also published, which | ||
you can find under the [`/es` folder](https://unpkg.com/@material-ui/core/es/). | ||
All the non-official syntax is transpiled to the [ECMA-262 standard](https://www.ecma-international.org/publications/standards/Ecma-262.htm), nothing more. | ||
⚠️ In order to minimize duplication of code in users' bundles, library authors are **strongly discouraged** to import from any of the other bundles. |
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.
Sorry for commenting on a closed PR, but is this recommendation saying for libraries to only import either /modern
or /legacy
? Or is it saying to keep imports as they were before, e.g. @material-ui/core/Button
(which would later be used alongside a Babel transform that repoints at either /legacy
or /modern
, when you build an actual app)?
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.
Libraries should not deal with from where they import. This should all be up to the bundler. So yes, import only from @materialui/*/*
in your library.
I repent for using this PR to ask a question, but it's a small one: Why does MUI distribution includes CommonJS? Won't all React components be bundled anyhow by a bundler that support What's the use case for a |
SSR maybe |
The ecosystem isn't ready for ES modules. For example, next.js requires CommonJS. |
Is it? NextJS is using webpack, which will prioritise I've got a library of React components and I'm transpiling it with I'm asking this question because to the best of my knowledge pretty much all React components are bundled using webpack (for the consuming app at least, not libraries) and webpack has been supporting esm for quite some time. |
Yes: vercel/next.js#23725
Are you sure you're using native ES modules and not some loose interpretation that bundlers used to use? For example, relative file imports do need a file extension. Once you have e.g. |
OK, probably my wrong (am I confusing between But, if I'm not wrong, the babel config I'm using is borrowed from how MUI used to build the env: {
esm: {
presets: [
[
'@babel/preset-env',
{
// Do not transform modules - keep as esm
modules: false,
targets: {
node: '6.10',
},
},
],
],
plugins: [['@babel/plugin-transform-runtime', { useESModules: true }]],
},
}, |
You're probably shipping something that is only understood by bundlers. With commonJS at least node understands it. With proper ES modules node, browsers and bundlers will understand the code. |
This comment has been minimized.
This comment has been minimized.
You do when doing server-side rendering. |
But this is done via webpack, which goes to the NextJS uses webpack. |
OK. I think I see what I'm missing. I've been with NextJS for too long probably... Some people (as in some React examples) do SSR where the server simply requires the React Component (no webpack involved). These people are unlikely to write cjs style - most likely they write es6 and have some transpiler for the code, but not for node_modules. So I guess the answer is - for people who do SSR without a bundler. |
Yes, the most simple SSR is to use |
presets: defaultPresets.concat(['@babel/preset-react', '@babel/preset-typescript']), | ||
plugins: [ | ||
module.exports = function getBabelConfig(api) { | ||
const useESModules = api.env(['legacy', 'modern', 'stable']); |
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.
Am I reading this right that legacy SHOULD use ESModules? This is almost certainly a mistake, right?
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.
I believe this stands for legacy ESM.
From microbundle readme:
"module": "./dist/foo.module.js", // legacy ES Modules output (for bundlers)
"exports": "./dist/foo.modern.js", // modern ES2017 output
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.
Am I reading this right that legacy SHOULD use ESModules? This is almost certainly a mistake, right?
Could you open an issue and fill out the template to describe the mistake? Discussions on merged PRs are oftentimes forgotten.
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.
I guess I thought legacy was for ancient browsers like ie11, it seems that I might be incorrect about that. Thanks for the explanation, sorry for the mis-informed question. Have a nice day.
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.
legacy is for IE11. But IE11 does not understand ES modules nor CommonJS modules i.e. the code always needs a bundler anyway at which point we might as well ship ES modules to help tree-shaking.
The targets of the default bundle are not final. They will be locked on release of
@material-ui/core@5.0.0
fromnpx browserslist --mobile-to-desktop "> 0.5%, last 2 versions, Firefox ESR, not dead, not IE 11, maintained node versions"
new Supported Platforms documentation
new "minimizing bundle size" guide
We now ship 4 bundles:
stable
(default, formerlyesm
) which targets a snapshot (on release) of> 0.5%, last 2 versions, Firefox ESR, not dead, not IE 11"
modern
(formerlyes
) which targets the last 1 version of evergreen browsers and active node (currently that is 14. We can't usecurrent node
since that would include odd-numbered version which is not intended for production code)node
(formerly default) which targets a snapshot (on release) ofmaintained node versions
legacy
which isstable
+ IE11/icons
only shipsnode
andstable
since the other two bundles don't do anything for size but would double the install size which can be problematic (though I haven't been able to reproduce these issues).I'm not implementing
exports
and ES modules for node yet. That would require considerably more effort (since we need to import with file extensions) and ES modules are still considered experimental on node (though I think they're planned to be stable in a couple of weeks I seem to recall).Closes #15496
Closes #18447
/cc @mui-org/core-team For input on the targets (see .browserslistrc).
Future work: