vite
vite copied to clipboard
[Vite version 3.0.0-alpha.9]: Treeshaking does not work with libs.
Describe the bug
[Vite version 3.0.0-alpha.9]: Cannot treeshaking libs.

[Vite version 2.9.9]: Its ok.

Reproduction
https://stackblitz.com/edit/vitejs-vite-bqjtx1?file=src%2FApp.tsx,vite.config.ts,stats.html
System Info
System:
OS: macOS 11.6
CPU: (8) arm64 Apple M1
Memory: 99.69 MB / 8.00 GB
Shell: 5.8 - /bin/zsh
Binaries:
Node: 16.13.0 - ~/.nvm/versions/node/v16.13.0/bin/node
Yarn: 1.22.17 - ~/.nvm/versions/node/v16.13.0/bin/yarn
npm: 8.1.0 - ~/.nvm/versions/node/v16.13.0/bin/npm
Browsers:
Chrome: 102.0.5005.61
Safari: 14.1.2
npmPackages:
@vitejs/plugin-legacy: ^1.8.0 => 1.8.2
@vitejs/plugin-react: ^1.3.2 => 1.3.2
vite: ^3.0.0-alpha.9 => 3.0.0-alpha.9
Used Package Manager
pnpm
Logs
$ pnpm run build
> [email protected] build /Users/sun/Desktop/work/vite-antd-seed
> vite build
vite v3.0.0-alpha.9 building for production...
✓ 42 modules transformed.
dist/assets/favicon.4b63ffc1.svg 1.49 KiB
dist/index.html 0.53 KiB
dist/assets/TestComponent.7cc13317.js 0.12 KiB / gzip: 0.13 KiB
dist/assets/index.0d2e4644.js 0.19 KiB / gzip: 0.17 KiB
dist/assets/index.2636713a.js 5.91 KiB / gzip: 2.51 KiB
dist/assets/esm-VW3YJATR.944f0927.js 214.24 KiB / gzip: 64.88 KiB
dist/assets/index.06cb8156.css 530.03 KiB / gzip: 67.17 KiB
dist/assets/vendor.8dd48daa.js 1696.88 KiB / gzip: 538.35 KiB
(!) Some chunks are larger than 500 KiB after minification. Consider:
- Using dynamic import() to code-split the application
- Use build.rollupOptions.output.manualChunks to improve chunking: https://rollupjs.org/guide/en/#outputmanualchunks
- Adjust chunk size limit for this warning via build.chunkSizeWarningLimit.
Validations
- [X] Follow our Code of Conduct
- [X] Read the Contributing Guidelines.
- [X] Read the docs.
- [X] Check that there isn't already an issue that reports the same bug to avoid creating a duplicate.
- [X] Make sure this is a Vite issue and not a framework-specific issue. For example, if it's a Vue SFC related bug, it should likely be reported to https://github.com/vuejs/core instead.
- [X] Check that this is a concrete bug. For Q&A open a GitHub Discussion or join our Discord Chat Server.
- [X] The provided reproduction is a minimal reproducible example of the bug.
The solution I found to this, prior to Vite Alpha-11 was to provide all files as entry point within build -> rollupOptions -> input as well as correcting import paths manually. At Alpha-11 I had to implement build -> rollupOptions -> output -> manualChunks with the following to resolve this issue.
SourceRootandNodeModulesRootshould be adjusted to point at the base of your source code. In most projects this is thesrcdirectory..tsfiles are assumed to be entry pointsSourceRootdirectory structure will be copied
import { extname, resolve } from "path";
export class ManualChuncker {
// Project
private static readonly SupportedFiles = [
"ts",
"vue",
"scss",
"scss?inline",
"js",
"json",
];
private static readonly SourceRoot = resolve(
__dirname,
"..",
"library",
"api"
);
private static readonly NodeModulesRoot = resolve(
__dirname,
"..",
"node_modules"
);
// Generated
private static readonly AssetDir = "_assets/";
private static readonly NodeModuleDir = "_external/";
private static readonly PluginDir = "_plugins/";
private static readonly VueDir = "_vue/";
public static resolve(path: string) {
return new ManualChuncker(path).resolve();
}
constructor(public readonly path: string) {}
public resolve(): string | void {
return this.moduleName;
}
private get moduleName() {
const CleanPath = this.path.substring(
0,
this.path.length - extname(this.path).length
);
if (this.isNodeModule) {
return `${ManualChuncker.NodeModuleDir}${CleanPath.substring(
ManualChuncker.NodeModulesRoot.length + 1
)}`;
}
if (this.isVue) {
return `${ManualChuncker.VueDir}${CleanPath.substring(
ManualChuncker.SourceRoot.length + 1
)}`;
}
if (this.isAsset) {
return `${ManualChuncker.AssetDir}${CleanPath.substring(
ManualChuncker.SourceRoot.length + 1
)}`;
}
if (this.isPlugin) {
return `${ManualChuncker.PluginDir}${this.path}`;
}
return CleanPath.substring(ManualChuncker.SourceRoot.length + 1);
}
private get isNodeModule() {
return this.path.startsWith(ManualChuncker.NodeModulesRoot);
}
private get isAsset() {
return (
this.fileType === "scss" ||
this.fileType === "json" ||
this.fileType === "scss?inline"
);
}
private get isVue() {
return this.path.endsWith(".vue");
}
private get isPlugin() {
return !ManualChuncker.SupportedFiles.map((ext) =>
this.path.endsWith(`.${ext}`)
).includes(true);
}
private get fileType():
| typeof ManualChuncker["SupportedFiles"][number]
| null {
const ext = extname(this.path).substring(1);
if (ManualChuncker.SupportedFiles.includes(ext)) {
return ext as typeof ManualChuncker["SupportedFiles"][number];
}
return null;
}
}
P.S. yarn publish doesn't seem to like the node_modules folder create (node_modules/vite/deps_build-dist) when you use the dist folder as the root of the package when deploying.
I'm not sure if it's related to this problem. When I run vite build for the first time, the packaged files are obviously not as big as those of the second vite build.
I can't reproduce this issue in a newly created project, below are screenshots of two runs what could be the problem?
- When the generated
.vitefolder does not exist undernode_module
- When the generated
.vitefolder existsunder node_module
I suspect it has something to do with the cache. When I set optimizeDeps.force to true, the files output by each build are different but the size is very close
^ I have the same problem
@ckvv @consegrado, would you share a repro as minimal as possible so we can build a bench for these issues. Thanks!
@patak-dev
This is a private project, and when I delete the src directory and add a simple case, the problem is not reproduced
@ckvv would you try with:
- https://github.com/vitejs/vite/pull/8965
@patak-dev
When I set optimizeDeps.disabled = "build", vite build throws an error

Have you tried https://github.com/vitejs/vite/pull/8965? Please open a new issue with a reproduction if you find a bug when using it
@patak-dev
updated to 3.0.0-beta.8 solved my problem
Thanks for testing @ckvv, we'll review the tree-shaking issues and try to flip the default in v4 to optimize deps again 👍🏼 Let's keep this issue open to track the problem
Woo! Great work of your team.
tree shaking does not work in 3.0.0-beta.8 and 3.0.0-beta.10
tree shaking does not work in 3.0.0-beta.8 and 3.0.0-beta.10
Have you tried 3.0.0 (non-beta/alpha)? Wasn't previously working for me with the alpha, but works perfectly fine with the major release.
I tried 3.0.0-beta.8 and 3.0.0-beta.10 and 3.0.0 and 3.0.2,tree shaking does not work
@patak-dev I recently hit a similar issue, where I had a third party library which could have been completely tree shaken out but was not. And enabling dep optimiser manually did fix the issue.
It was a bit weird for me, as I expected better tree shaking without dep optimisation, as I believe dep optimisation is done without knowledge of what is actually imported from the lib.
I'm on vite 3.1.0 and tree shaking not working at all
import { fill } from "lodash";
console.log(fill([], ""));
will includes all the lodash functions
@kresli please share your configuration, I had to manually enable dependency optimisation to get tree shaking in lib mode
{
optimizeDeps: {
disabled: false
},
build: {
commonjsOptions: {
include: [],
},
rollupOptions: {
treeshake: 'smallest',
}
}
}
@kresli tree-shaking doesn't work on lodash (it has nothing to do with vite, rollup, or esbuild).
For those who want tree-shaking with lodash, there's lodash-es package.