preface

The purpose of this article is to share my scaffolding and some of the lessons learned during the development process.

Reading this article first can be regarded as just a new tool to understand, and because of the webpack and Vite bidirectional description, there will be a certain amount of vite and Webpack content parsing in the middle. (The main idea analysis does not involve specific source code, interested in their own to read the source code)

Those who are not interested in analysis can jump right into the V5-run summary

# A wave of old rulesVue component platform server recently made a new server, welcome to try! I'm also available if you want to leverage your company's component analysis platform. The project adopts Docker deployment, which can be very convenient to build an internal platform of the company. Online access to the address: http://assemble.everbeon.top/assemble/#/Show/index note: animation card too background particles can click on the top right corner of the small icon can close background animationCopy the code

How do I get Webpack to have vite speed

webpack vs vite

First of all, we will carry out two sections of analysis on this question. What is the reason why Webpack is slow and Vite is fast?

webpack bundle everything

Yes, that’s why WebPack is slow, because WebPack precompiles all running resources, parses dependent modules, and ends up packing modules into memory.

vite Bundleless esbuild esmodule

In Vite, the opposite is true, following a low-packing, pre-processing approach that allows Vite to rely on packaging only the first time it runs (package.json unchanged). It also relies on the EsModule to import files directly at run time, so that files are not packaged together, and esbuild parsing transforms for syntax (e.g. Ts, JSX, etc.) in this way, there is no need for JS parsing ast syntax tree and then rebuilding, which can first save a lot of CPU and memory space, and second reduce a lot of time for grammar parsing. Basically, it can achieve timeliness without grammar parsing in advance.

why webpack

In the development of Webpack, we are more or less using the convenience brought by webpack’s “dialect”. For example:

// require.context Api
require.context(directory, useSubdirectories, regExp)
...
// CSS exports variables to js
:export {
    theme: $--color-primary; }...// Various magical paths
import App from 'App'.// And SVG is introduced
<use :xlink:href="iconName" />
Copy the code

It can be said that Webpack has spoiled us while bringing us convenience! More and more, the ES specification deviates from the standard, giving us more and more back doors, and we can even write some Node apis in our pages. (Looking forward to more convenient backdoors.) Migrating webPack to Vite in this case led to a series of errors, and rollup caused uncertainty in our project due to unfamiliar configuration files. So I don’t want to touch my original project and it’s like experiencing vite flying is my initial goal.

how to do

How many steps to put an elephant in the refrigerator?

  • Open the refrigerator door
  • Put the elephant in
  • Close the refrigerator door

Yes, our principle is also very simple if the elephant, any complex problems can be simplified, and do not think of the problem is too complex is the fastest way to solve the problem

Our main content is also divided into three steps

Build the URL and syntax parsing service

The main purpose of this step is to have our scaffolding support webPack-specific path preprocessing judgments and parse our VUE files properly.

Tripartite dependency processing

This step is handled as a collection of dependencies and has it imported as an import, equivalent to vender handling in WebPack

Webpack dialect API implementation

Implement special apis for Webpack, such as :export {}, require.context

This completes our entire target path. Of course, if you simply list the architecture, you probably need a diagram like this to achieve.

Of course, processing webpack dialect implementation (can not be integrated into this, that is a specific requirement), you will find that the tripartite dependency is not in the design, next we will focus on this tripartite dependency (involving a certain principle of vite analysis, can understand the interview brag).

why first node_modules

Why do you need to build third-party dependencies ahead of time in Vite? The official website explains the following two points:

  • CommonJS and UMD compatibility
  • performance

But! It doesn’t seem to be a problem to build with esBuild for compatibility and performance, and one of the hidden benefits of not pre-build is to reduce node_modules dependencies at runtime. For example, we can manually implement a yarn-like centralized package management. So we can implement node_modules in our project perfectly, which is exciting to think about. So what’s the problem?

There is an option in esbuild called Bundle: True

This option packs all dependencies of the entry file that need to be packaged. For example, if I import ElementUi, it pushes all dependencies that Element needs inside. (important! Please remember)

When we introduce elementUI at this point, is the VUE used inside elementUI the same as the VUE in the project itself?

Answer: No, because Elementui introduces its own internal VUE, while the project introduces a separate VUE

How exactly is WebPack introduced?

If you look at node_modules, you’ll find that elder-UI requires a lot of dependencies, but it has few or no dependencies. These dependencies are usually at the first layer of node_modules. What are the results?

In the same project, different projects depend on the same NPM, their imports are the same, and the reference values are equivalent to their sharing of the export of the NPM. For example, when a.js introduces xxx.js and changes the exported ceshi value to 2, then when B. js introduces the exported ceshi value to 2 instead of the original ceshi value.

At this point we found the biggest problem, loading dependencies at runtime does not analyze their reference relationships, which can lead to the biggest hidden problem!!

Therefore, the biggest problem of vite preprocessing lies in the dependency between the three packages.

Why can vite be preprocessed for analysis

The answer is simple, because vite needs to add a script import of type=”module” to the HTML of the import, and then use the import that matches the script import as the import file of the esbuild. In this way, esBuild looks for dependencies through the import file and then adds plug-ins to analyze the state of dependency introduction, thus implementing a preprocessing analysis that feels smart.

v5-run

This is the magic instruction that gives WebPack the speed of Vite, and the implementation follows it.

So here is mainly on the use of scaffolding and configuration. (Currently only available for VUE2 development)

Address collection

NPM: www.npmjs.com/package/@se…

Gitee: gitee.com/beon/v5-vue…

NPM installation: NPM i@seeyon-v5-vue/cli-run-g

Run instruction: V5-run

The configuration file

Like any configuration file, you need to create a v5-run.config.js file in the project root and export it to the configuration object.

module.exports = {
    // Configure the service to run
    server: {
        // Same as webpack Proxy
        proxy: {
            [url: string]: {
		target: string, host? : string, headers? : {[key: string]: string} changOrigin? : Boolean}},// Whether to enable http2 mode.Http2:Boolean.[' SRC/HTML /'] [' SRC/HTML /']
        enter: string []},// The configuration of various SettingsConfig: {// Configure SVG to be imported into HTMLSvgLoader: {// Import the SVG folder path
            path: string,
            // SVG import name configuration example :my-svg- [name], import name (SVG file name app.svg) : my-svG-app
            symbolId: string
        },
        // Import less and SCSS globally
        styleLoader: {
            [' SRC /assets/index.scss']
            [loadStyle: string]: string[]
        },
        // Global variable configuration such as _(loadsh)
        global: {
            [loadsh, map] [loadsh, map] [loadsh, map] [loadsh, map] [loadsh, map
            [name: string]: string | string[]
        }
    }
}
Copy the code

Using the tutorial

Step 1 Configure the v5-run.config. file

The basic configuration file can be changed as required

module.exports = {
    server: {
        enter: ['./src'].http2: true.proxy: {
            "/dev-api": {
		target: 'http://localhost'.changOrigin: true}}},config: {
        svgLoader: {
            path: 'src/icons'.symbolId: 'icon-[name]'
        },
        global: {
            _: "lodash".$: "jquery".jQuery: "jquery"
        },
        styleLoader: {
            less: [path.resolve(__dirname, "./src/assets/styles/variable.less")]}}};Copy the code

The second step executes the V5-run command

If the service is successfully started, the service is successfully started

Step 3 Visit the website (note)

The web access path requires manual input to your entry documents, such as: http://localhost:3000/src/html/index.html second, join index. The best HTML path, otherwise there may appear some path parsing a layer of less problem. Access to the error will be prompted, and there will be a problem will be prompted page, you can double-click the error request page to view the cause of the error

Trouble spots

This section, as a separate description, mainly emphasizes the important function points that should be implemented but are not implemented at this stage.

No hot update

Hot update has not been done for the time being. Although there are existing examples, hot update is of little significance for my own use only (the project is special).

Webpack compatibility

As for compatibility, only a few common Settings and configurations are made, which can meet most standard projects. Special projects need special treatment, which cannot be solved for the time being. If you have any problems, you can contact me directly and check the defects of scaffolding (maybe it will be fixed in the next version).

Tripartite dependencies are handled each time they are enabled

In fact, this is a relatively easy to deal with the problem, but I found that the processing time is short when using, so temporarily did not deal with (is lazy).

Path handling in CSS files

$– text-path: “~ elemental-ui /lib/theme-chalk/fonts”; $– text-path: “~element-ui/lib/theme-chalk/fonts”; (Only parameters need to be added, @import and normal URL are not needed)

At the end

If you are interested in gitee, you can also see that this project is only one part of the whole scaffold project, and the rest of the content has not been added. In the later stage, the treatment method, agent method and management three-party package method will be all pulled out to make a complete scaffold project. Now we are just making the feasibility of the project. The overall project was developed using TS, but there was no specific split so there was no unit test.

As a new scaffolding content, I think improving development efficiency and project stability is the most important, which is why there is no forced replacement of Vite as production, when problems can be directly dealt with using WebPack. (such as: IE situation, compatibility testing, etc.) So the project is a trial phase for us to switch to using ESModule, let’s make webpack have the same speed as Vite in a disguised way.

The three-party dependency processing in this project is based on Vite to some extent, so the current code is relatively similar, which is why I did not rush to initialize the cache information, because the target is different in the future, so I will modify the content of this block later.

This is all the content of this article, welcome to discuss, I wechat :Dawn_web, QQ: 962717593, any questions can contact me.

I’m BEON, a front end engineer who tries to find ways to help the team be more efficient