xxx does not provide an export named ‘xxx’

Most third party packages are CJS exports, that is, only one export, such as Axios, jquery, LoDash, etc. They export in a similar way

module.exports = require('./xxx');
Copy the code

Obviously, this is not recognized by Vite, because Vite only supports ESM export, and these third-party packages need to be compatible.

Fortunately, Vite now has a precompilation feature that precompiles these third-party packages into ES modules and places them in the node_modules/.vite folder. Similar to the following

So for these third-party packages, if it’s a CommonJS specification, we don’t care that Vite will handle it for us by default

Uncaught ReferenceError: require is not defined

This is probably the one that comes up the most, because Vite is completely ESM native, meaning it only knows the import, because Vite relies on the Module property of script. Our code will eventually be sent to the browser to execute, require is the CJS keyword, the browser environment does not define this method, naturally error. Unlike WebPack, which prepackages the file before sending it to the browser, require has already been converted into a browser-compatible method. (This is probably because the ES6 module uses require as a dependency, but the ES6 module uses require as a dependency. When Vite builds the ES6 module, it does not precompile because it uses import.)

If it is a self-written module, change it to import. If it is a third-party module, it may need to patch the source code with patch-package

antd3

Through the call stack we found is in node_modules/antd/es/icon/index has written the following code in js

import * as allIcons from '@ant-design/icons/lib/dist';
// ...
ReactIcon.add.apply(ReactIcon, _toConsumableArray(Object.keys(allIcons).map(function (key) {
  return allIcons[key];
})));
Copy the code

Keys (allIcons). In allIcons, there will be a default attribute, which should be added by the packaging tool, but because there is a default attribute in this attribute, the following code has a problem. Therefore, patches can be used to create a patch for the source code. For specific reasons, please refer to CommonJS compatibility issues encountered during the use of Vite in this article

import allIcons from '@ant-design/icons/lib/dist';
Copy the code

global is not defined

This is because there is no global attribute added to index.html in the browser

<! -- index.html -->
<html>.<body>
    <script>
      global = globalThis
    </script>.</body>
</html>
Copy the code

Error: ‘CombineService’ is not exported by node_modules/@umijs/use-request/lib/types.js, imported by node_modules/@umijs/hooks/es/useFormTable/index.js

Node_modules /@umijs/use-request/lib/types.js is an empty file

module.exports = {};
Copy the code

decorators not support in js for prebuild

Esbuild does not currently support the use of decorators in JS, as decorators are not yet written into the ES standard, but our projects may already use decorators, such as mobx projects, so we need to use TS to support decorators. Related issue: github.com/vitejs/vite… Github.com/evanw/esbui…

Dynamic require of “node_modules/antd/lib/style/default.less” is not supported

When we use ANTD, we introduce components

import {Menu} from 'antd';
Copy the code

But the default imported components are imported from node_modules/antd/lib, where the imported styles are referenced as follows.

"use strict";

require(".. /.. /style/default.less");
require("./index.less");
require(".. /.. /tooltip/style");
Copy the code

We need to install viet-plugin-importer and make the following configuration in viet.config. js

// vite.config.js
import usePluginImport from 'vite-plugin-importer';
import { defineConfig } from "vite";

export default defineConfig({
    plugins: [
        usePluginImport({
          libraryName: 'antd'.libraryDirectory: "es".style: 'css',})]})Copy the code

So we load modules from the ES folder

import '.. /.. /style/default.less';
import './index.less'; // style dependencies
import '.. /.. /tooltip/style';
Copy the code

Environment variable injection

In the previous WebPack project, we used process.env.xxx to set environment variables. The process object does not exist in the browser environment. Webpack did the conversion for us, and we can use a similar configuration when using Vite

{
    define: {
        'process.env.APP_ENV': JSON.stringify(process.env.NODE_ENV),
        'process.env.APP_REGION': JSON.stringify(process.env.APP_REGION),
    }
}
Copy the code
export const APP_REGION = process.env.APP_REGION || 'id';
export const APP_ENV = process.env.APP_ENV || 'test';
export const SENTRY_RELEASE = process.env.SENTRY_RELEASE || 'dev';
export const NODE_ENV = process.env.NODE_ENV || 'development';
Copy the code

Const {APP_REGION} = process.env;} {APP_REGION} = process.env;

Of course, we can also use.env configuration

vite --mode dev
Copy the code

Then provide.env.dev

VITE_APP_ENV='dev'
VITE_APP_REGION='id'
Copy the code

What if you need multiple schemas, such as Node environment and country, with two parallel schema environment variables and schemas

The plug-in

vite-plugin-optimize-persist

One is the pre-built plug-in vite-plugin-optimized-persist. There will be many dynamic dependencies in our business code, and it will be difficult to set them one by one in the vite configuration optimizeDeps include, especially if you need to set them to a specific file path rather than just to the root directory. If you don’t set it, you’re still going to have to wait a long white screen time for it to be pre-built when it’s first loaded at development time. This plug-in automatically adds dynamic dependency analysis to the include of optimizeDeps so that someone else doesn’t have to wait for the first run of downloaded source code even if there is no cache.

Problem solved: Some pages are loaded by lazy, also load the dependency inside, will be precompiled, and this process will wait, resulting in the page blank screen problem. The dependencies must be compiled in advance when the plug-in is launched, and they are automatically written to the package.json vite field.