9
头图

background

A two-year development of the company’s two-year project needs to be split due to the need to expand more business segments in the later period. One is to ensure that the continuous addition of business segments in the later period does not affect the existing business, and the other is that the current single project business volume is too large. , Development and maintenance are extremely difficult, so we have to consider splitting the existing business segments into microservices to meet the later needs.

This article is a technical sharing of the implementation process of the title using the technology stack, and it is also an exploration and practice of the technical solution. If you are interested, please stay!


lerna

A tool for managing JavaScript projects with multiple packages.

Mainly used for the management of public dependencies in the production phase of microservices. Problems that can be solved: During the development phase, multiple services are started at the same time, and the subprojects do not need to be placed in the same git project. Some npm private server packages in the enterprise can be updated to various subprojects more conveniently, and some public dependencies can be installed in the root directory of lerna Save some storage space.

Get started quickly

PS: Here you need to create an empty project directory first, the following examples are all umi-qiankun-explore
It is recommended to lerna globally, of course, it can also be installed locally

npm i lerna -g

initialization

lerna init --independent //installed globally
npx lerna init --independent //install locally

The main method is to install dependencies for a project individually, or install public dependencies for all sub-projects. For the specific supported parameters, see lerna bootstrap

lerna bootstrap <--options>

The initialized lerna project directory is as follows

umi-qiankun-explore/
|--packages/ //这里是存放微服务各模块等目录,后面已更改为project,对应需要调整的配置见下方lerna.json▼
|--package.json
|--lerna.json

umi-qiankun-explore/lerna.json

{
  "packages": ["project/*"],
  "workspaces": ["project/*"],
  "version": "0.0.0"
}

umi-qiankun-explore/package.json

{
  "name": "root",
  "private": true,
  "scripts": {
    "clone:all": "bash ./cli/clone-all.sh", // 这里用来可以根据设备写一个clone所有子项目的脚本
    "boots": "lerna bootstrap --hoist", // 安装子项目所有公共的依赖
    "start": "lerna run --parallel  start " //启动所有子项目
  },
  "devDependencies": {}
}

Modifying the directory here is mainly to switch the directory p plus Tab under the command line, which will also bring out package.json, which is not very convenient 😄

umi

Use umi create subprojects in project create a project module is divided according to the actual situation of micro-services directory, will be created using the same way respectively app-container , app-device , app-common three projects.
Among them, app-container main project, the container for microservices, and generally only has basic business functions such as page layout, login authorization, and basic data distribution.
app-common mainly used as a project's public business module, and generally has basic functions such as account information management and application settings that are irrelevant or not strongly related to specific businesses.
Other sub-projects can be divided according to the actual situation of the project.

After creating three new project directories, create a project through official tools

yarn create @umijs/umi-app / npx @umijs/create-umi-app

⚠️ Note: After creating the project, you need to do two basic things, which are very important

  • Change the name attribute in the package.json of each project to the corresponding name of the project
  • The original start start command of each project needs to specify the port number, as follows

In this example project, container corresponds to 8000, common corresponds to 8002, and device corresponds to 8001

 "start": "PORT=8001 umi dev set"

Since then lerna has come in handy, add the public dependencies of each umi project in umi-qiankun-explore/package.json

"dependencies": {
    "@ant-design/pro-layout": "^6.5.0",
    "@umijs/plugin-qiankun": "^2.27.0",
    "react": "17.x",
    "react-dom": "17.x",
    "redux-thunk": "^2.3.0",
    "umi": "^3.5.15"
  },
  "devDependencies": {
    "@types/react": "^17.0.0",
    "@types/react-dom": "^17.0.0",
    "@umijs/preset-react": "1.x",
    "@umijs/test": "^3.5.15",
    "lint-staged": "^10.0.7",
    "prettier": "^2.2.0",
    "typescript": "^4.1.2",
    "yorkie": "^2.0.0"
  }

At this time, use npm run boots to complete the installation of the public dependencies of each sub-project. After installing the project dependencies, we can use npm start to start each project at the same time, but at this time the project has not micro-up 1610d163f6aff0. The project directory structure that can be obtained after completing the above steps is as follows:

Directory structure (key part)

umi-qiankun-explore
├── project
│ ├── app-common
│ │ ├── mock
│ │ ├── src
│ │ ├── .umirc.ts
│ │ ├── package.json
│ │ └── ...
│ ├── app-container
│ │ ├── config
│ │ ├── mock
│ │ ├── src
│ │ ├── README.md
│ │ ├── package-lock.json
│ │ ├── package.json
│ │ ├── tsconfig.json
│ │ ├── typings.d.ts
│ │ └── yarn.lock
│ ├── app-device
│ │ ├── mock
│ │ ├── src
│ │ ├── .umirc.ts
│ │ ├── package.json
│ │ └── ...
├── lerna-umi-qiankun 搭建微服务过程.md
├── lerna.json
├── package-lock.json
└── package.json

plugin-qiankun

Adopt umi's official recommendation method to introduce qiankun into each project

yarn add @umijs/plugin-qiankun -D

Main project app-container

Here we first introduce the sub-projects in the way of routing binding. For the MicroApp component method, see using the <MicroApp /> component method

Add the following configuration in .umirc.ts

export default defineConfig({
  qiankun: {
    master: {
      // 注册子应用信息
      apps: [
        {
          name: 'app-common', // 公共服务
          entry: '//localhost:8002',
          // 子应用通过钩子函数的参数props可以拿到这里传入的值
          props: {
            token: 'XXXXXXX',
          },
        },
        {
          name: 'app-device', // 设备服务
          entry: '//localhost:8001',
          // 子应用通过钩子函数的参数props可以拿到这里传入的值
          props: {
            token: 'XXXXXXX',
          },
        },
      ],
      jsSandbox: true, // 是否启用 js 沙箱,默认为 false
      prefetch: true, // 是否启用 prefetch 特性,默认为 true
    },
  },
})

Assuming that our page layout mainly relies on the main project, the way to introduce sub-project routing is as follows

export default defineConfig({
  routes: [
    {
      exact: false,
      path: '/',
      component: '@/layouts/index',
      routes: [
        {
          path: '/home',
          component: '@/pages/home/index',
          meta: { title: '首页' },
        },
        // 公共服务模块
        {
          name: 'app-common', //⚠️注意这里需要与上面qiankun配置的name相对应
          path: '/common',
          microApp: 'app-common',
        },
        // 设备服务模块
        {
          name: 'app-device',
          path: '/device',
          microApp: 'app-device',
        },
      ],
    },
  ],
})

Subproject app-common

In .umirc.ts in new configurations to support qiankun

import { defineConfig } from 'umi'

export default defineConfig({
  nodeModulesTransform: {
    type: 'none',
  },
  routes: [{ path: '/', component: '@/pages/index' }],
  // 新增配置
  qiankun: {
    slave: {},
  },
})

The life cycle of the sub-project needs to be exported. The umi@3.5 version initialization has no app.tsx file, so we need to create a new one manually.

/src/app.tsx

export const qiankun = {
  // 应用加载之前
  async bootstrap(props: any) {
    console.log('子应用[app-common] bootstrap', props)
  },
  // 应用 render 之前触发
  async mount(props: any) {
    console.log('子应用[app-common] mount', props)
  },
  // 应用卸载之后触发
  async unmount(props: any) {
    console.log('子应用[app-common] unmount', props)
  },
}

app-device has the app-common method as 0610d163f6b331, so the basic structure of the microservice project is initially completed.
The above is only the first step of microservices under the current technology stack. As for the practical application of , there are still many 1610d163f6b34d pits, such as style isolation, data sharing, data up and down, etc. Qiankun is currently dealing with not comprehensive problems. It is still necessary to troubleshoot and upgrade according to the actual situation of the project.

So far, the preliminary practice of the overall technology stack has been completed. Of course, for lerna , umi.js and qiankun there are more high-level business scenarios that are not involved, mainly because the characteristics of each project have different entry points for the application of these technologies, so this article We only need to guide the follow-up more complex scenes or we need to go to to solve specific problems.

Leaving the picture shows that the implementation of the micro front end can be completed according to all the above steps, hahaha!

fuCOpR.md.png

Interested students can move to github to pull up my project demo, and more complex problems in actual scenarios will be improved later.
github

The article is not from cv, if it is helpful to you, please don’t hesitate to like it below 👇, thank you! 😁😁😁

Reference article


vannvan
699 声望54 粉丝

Be a moral integrity programmer!