Mono repo and workspaces
Theoretical basis of mono repo
What are Mono repo and Multi Repo?
A Monorepo is a version control code library that holds many projects. Although these projects may be related, they are usually logically independent and run by different teams.
Monorepos is sometimes called a singleton repository. Some companies host all their code in a repository for everyone to share.
Characteristics of mono repo
In common
- Independence: Each project is independent, that is to say, can be taken out separately. Mono-repo is relatively independent, and multi-repo is absolutely opposed
Advantages and disadvantages of Mono Repo
- Visibility is strong
- Easier dependency management
- participatory
- unity
- The learning curve
- Poor performance
- A large amount of data
- Version control
- .
Who supports Monorepo’s Workspace
In order to manage multiple parallel code bases (monorepo) in a single file, the workSpaces feature was born out of the management tool.
- Yarn supports the workspaces function
- Npm7 began supporting workspaces functionality
- PNPM supports workspaces functionality
- The Lerna named row tool supports managing workspaces
Yarn workspace example
1. Start a monorepo using YARN
mkdir <project_name>
cd <project_name>
yarn init -y
Copy the code
Note that the following two fields must exist:
- Field version
- The field name
2. Modify package.json file to add workspaces/private fields
{
"private": true.// Must be a private package
"name": "<your_project_name>"."version": "1.0.0"."workspaces": [
"packages/*".// Make all files under all packages as mono repo]."main": "index.js"."license": "MIT"."dependencies": {
"lodash": "^ 4.17.21"}}Copy the code
3. Manually add the project1/project2 project folder
├ ─ ─ package. Json # top-level package. Json ├ ─ ─ packages │ ├ ─ ─ project1 # mono repo 1 │ └ ─ ─ project2 # mono repo 2 └ ─ ─ yarn. The lockCopy the code
After the folder is created, initialize both projects, because only after initializing both projects, use the related command of workspace, otherwise yarn task project1/project2 is not a project.
cd packages/project1
yarn init -y
cd ../packages/project1
yarn init -y
Copy the code
Of course, if you are using a framework such as UmiJS/Vue, you can use its scaffolding tool to initialize a project.
4. Write code in project1/ Project2
Mono repo commands
yarn workspace <workspace_name> <command>
Copy the code
For example, we would use React to develop the project in project1, executing in the project root directory:
yarn workspace project1 add react react-dom
Copy the code
In Project2 we added vUE
yarn workspace project2 add vue vue-router vuex
Copy the code
After installation, you can view the root package.json file unchanged, but the project1/project2 project package.json has changed. Node_modules is not generated in the project1/project2 installation package of the YARN Workspace command. The dependency packages of both projects are placed in the root node_modules.
5. Build Project3 using the common @umijs
cd packages/
mkdir project4 && cd project3
yarn create @umijs/umi-app Node_modules will not be installed
Install node_modules manually
cd porject3
yarn workspace project3 install
# Start the UMI service
yarn workspace project3 start #http://localhost:8000
Copy the code
6. Build Project4 using the usual @vue/ CLI
cd packages/
vue create project4 # vue will help us install it
cd project4
rm -rf node_modules
cd. /.. / yarn workspace project4 install# @vue/cli automatically installs, generating a node_modules
cd project4 && rm -rf node_modules
cd. /.. / && yarn workpsace project4 install## Start vue service
yarn workspace project4 serve # http://localhost:8080/
Copy the code
PNPM workspace sample
Note node.js version support (version 12 recommended)
1. Initialize a PNPM monorepo project
cd your_project
pnpm init -y
Copy the code
2. Create a pnpm-workshop. yaml monorepo configuration file.
touch pnpm-workspace.yaml
mkdir packages && cd packages && mkdir project1 project2
# Add.npmrc file to subproject root
cd packages/project2 && touch .npmrc
cd ../project1 && touch .npmrc
Copy the code
Configure the pnpm-workshop. yaml file
packages:
- 'packages/**'
Copy the code
Also note that under the workspace project, add the.npmrc configuration file.
3. Manually add dependencies to project1/project2
PNPM uses the add/install command to add the workpakce package, and adds the filter
flag in the workpakce file.
Add LoDash to the top layer for testing
cd project
pnpm add lodash
Add the React project to Project1
pnpm add react react-dom --filter project1
## Add the VUE project to Project2
pnpm add vue vue-router vuex --filter project2
Copy the code
After installation, write dependencies under the corresponding package.json, in the package.json directory
4. Use @umijs to generate the React project
cd packages && mkdir project3
cd project3 && pnpx @umijs/create-umi-app
# add name field to umijs package.json file
"name": "project3"
cd ../ && pnpm install --filter project3
## Start umiJS service
pnpm run start --filter project3 # http://localhost:8000
Copy the code
5. Use @vue or cli to generate the React project
cd packages && vue create project4
# vue will install node_modules, which needs to be removed and reinstalled in the root directory
cd project4 && rm -rf node_modules
# reinstall
pnpm install --filter project4
# start service
pnpm run serve --filter project4 # http://localhost:8080/
Copy the code
Npm7 workspace sample
NPM workspace is different from YARN/PNPM workspace. Its main functions:
NPM workspace compensates for the more simplified workflow of processing linked packages from the local file system. As part of the automated linking process, NPM Install avoids manually using NPM link to add references to packages that are symlinked to the current node_modules folder.
That is, the packages defined in NPM Workspace are for sharing. The goal is to simplify the linking of NPM link
NPM workspace use example
Initialize a root project
cd your_path && mkdir your_project && cd your_project
npm init -y
# add lodash
npm i lodash
Copy the code
1. Enable the workspace function
Note: NPM supports workspace as of version 7.
"name": "your_name"."workspace": [
"./packages/*"
]
Copy the code
2. Create the React project
cd packages
npx create-react-app app1
Copy the code
3. Install in the following directory (or link app1 module)
cd ../
npm install app1 --workspace=app1
Copy the code
We now have the app1 package in workspace installed in the root directory and can use app1 just like any other package.
Lerna Mono-Repo management tool
Lerna can be understood as a command-line tool for mono-repo.
1. Install lerNA globally
npm install --global lerna
yarn global add lerna
Copy the code
Git must be initialized with lerna:
cd your_project_path && mkdir your_project && cd your_project
git init
Copy the code
3. Run the lerna command to initialize a project
lerna init
Copy the code
The resulting directory structure after lerna initialization
.├ ── ├─ package. ├─ ├─ ├.json ├─ ├.txtCopy the code
4. Use the lerna command line to create a two-word command
lerna create project1
lerna create project2
Copy the code
Look at the directory again:
. ├ ─ ─ lerna. Json ├ ─ ─ package. The json └ ─ ─ packages ├ ─ ─ project1 │ ├ ─ ─ the README. Md │ ├ ─ ─ __tests__ │ │ └ ─ ─ project1. Test. Js │ ├ ─ ─ lib │ │ └ ─ ─ project1. Js │ └ ─ ─ package. The json └ ─ ─ project2 ├ ─ ─ the README. Md ├ ─ ─ __tests__ │ └ ─ ─ project2. Test. The js ├ ─ ─ lib │ └ ─ ─ project2. Js └ ─ ─ package. The jsonCopy the code
5. Run the subproject script using lerna
Essentially the same as NPM, except that NPM is changed to lerna
lerna run test
Copy the code
Note: you must switch to each package
6. Simple analysis of the lerna command
- Lerna Bootstrap installs the NPM package into node_moduels in the root directory.
- Lerna exec executes commands in packages
lerna exec -- < command > [..args]
7. Lerna configuration file
{
"useWorkspaces": true.// Use workspaces configuration. If this is true, package.json's "workspaces" will be used and the following "Packages" fields will not take effect
"version": "0.1.0 from".// All package versions, independent mode -"independent"
"npmClient": "yarn".// NPM client, which can be set to YARN
"packages": [ // Package directory. Multiple directories can be specified
"packages/*"]."command": { // Lerna commands are configured
"publish": { // Publish related
"ignoreChanges": [ Publish is not triggered by changes to specified files or directories
".gitignore"."*.log"."*.md"]},"bootstrap": { / / the bootstrap
"ignore": "npm-*".// Package that is not affected by bootstrap
"npmClientArgs": [ // bootstr executes the argument
"--no-package-lock"]}}}Copy the code
8. Cooperate with the YARN workspace
There is no workspace for initializing lerna. After the workspace is marked, the rest will be the same as described above.
Version management of Mono-repo
reference
- Machine-specific docs.npmjs.com/cli/v7/usin…
- Simplify Your Monorepo with NPM 7 Workspaces dev.to/ Limal/Simpl…
- What is monorepo? (and should you use it?) Semaphoreci.com/blog/what-i…
- lerna lerna.js.org/