[TOC]
>[success] # node_modules 层级
~~~
1.在 npm 的早期版本, npm 处理依赖的方式简单粗暴,以'递归的形式',在npm3版本
后采用了'扁平结构'
~~~
>[danger] ##### npm2.x 版本node_modules 层级
~~~
1.执行 'npm install' 后,'npm' 根据 'dependencies' 和 'devDependencies' 属性中指定的包
来确定第一层依赖,npm 2 会根据第一层依赖的子依赖,递归安装各个包到子依赖的
'node_modules' 中,直到子依赖不再依赖其他模块。执行完毕后,我们会看
到 './node_modules' 这层目录中包含有我们 'package.json' 文件中所有的依赖包,而这些
依赖包的子依赖包都安装在了自己的 'node_modules' 中 结构目录:
├── node_modules
│ ├── A@1.0.0
│ │ └── node_modules
│ │ │ └── D@1.0.0
│ ├── B@1.0.0
│ │ └── node_modules
│ │ │ └── D@2.0.0
│ └── C@1.0.0
│ │ └── node_modules
│ │ │ └── D@1.0.0
~~~
* 结构层级图
![](https://img.kancloud.cn/7c/49/7c49d39e574b71f073e2312e8169d32a_842x322.png)
~~~
1.果你依赖的模块非常之多,你的 node_modules 将非常庞大,嵌套层级非常之深,
出现下图的效果,并且也会导致接下来的问题
1.1.在不同层级的依赖中,可能引用了同一个模块,导致大量冗余,举个例子当我的 A,
B,C 三个包中有相同的依赖 D 时,执行 npm install 后,D 会被重复下载三次
1.2.在 Windows 系统中,文件路径最大长度为260个字符,嵌套层级过深可能导致不可
预知的问题。
~~~
![](https://img.kancloud.cn/8a/9c/8a9c81a778100b1f2f19126325628378_1280x859.png)
>[danger] ##### npm3.x 版本
~~~
1.npm3.x 版本后采用了扁平化的解决方案,把依赖以及依赖的依赖平铺'node_modules'
文件夹下共享使用,npm 3 会遍历所有的节点,逐个将模块放在 'node_modules'的第一
层,当发现有重复模块时,则丢弃, 如果遇到某些依赖版本不兼容的问题,则继续采用
npm 2 的处理方式,前面的放在 'node_modules' 目录中,后面的放在依赖树中。
'过程说明':
下图 'A','B' 都依赖'D(v0.0.1)'那么在安装的时候将'A'的依赖包都平铺到'node_modules',
即将'D(v0.0.1)'平铺到了'node_modules' ,此时到了安装B包发现B包依赖在
'node_modules' 根已经重复这时候就跳过了,但是安装C的时候发现C也依赖'D'但是
依赖的版本不同,如果将C依赖的'D'放到'node_modules'根就因为重名问题覆盖掉
此时解决方案就像'npm2.x'的时候就将C依赖的'D(v0.0.2)'安装到了C的'node_modules'
下
~~~
* 如图
![](https://img.kancloud.cn/9f/49/9f4910f400ba6844c68e125c924ae165_562x302.png)
* 是否解决npm2的 问题
~~~
1. 'A','B' 都依赖'D(v0.0.1)' ,'C' 依赖'D(v0.0.2)',如果先安装C 此时 在安装A,B时候由于
在安装'C'的时候'D(v0.0.2)' 被平级安装在'node_modules',因此'A','B''node_modules'
下都会有一个''D(v0.0.2)'
npm 3 并未完全解决冗余的问题,甚至还会带来新的问题
~~~
* 如图
![](https://img.kancloud.cn/3b/19/3b193551344a0cbac5159f0b40b60463_563x272.png)
>[info] ## 参考
[npm 依赖管理中被忽略的那些细节
](https://www.infoq.cn/article/qj3z2ygrzdgicqauaffn)
>[danger] ##### npm5.x 版本
~~~
1.从npm 5.x开始,安装组织node_modules和npm 3.x一样采用了扁平化的方式,最大的变化是增加了 package-lock.json 文件,npm 3.x有的问题他也有
2.package-lock.json 中已经缓存了每个包的具体版本和下载链接,不需要再去远程仓库
进行查询,然后直接进入文件完整性校验环节,减少了大量网络请求
~~~
- 工程化 -- Node
- vscode -- 插件
- vscode -- 代码片段
- 前端学会调试
- 谷歌浏览器调试技巧
- 权限验证
- 包管理工具 -- npm
- 常见的 npm ci 指令
- npm -- npm install安装包
- npm -- package.json
- npm -- 查看包版本信息
- npm - package-lock.json
- npm -- node_modules 层级
- npm -- 依赖包规则
- npm -- install 安装流程
- npx
- npm -- 发布自己的包
- 包管理工具 -- pnpm
- 模拟数据 -- Mock
- 页面渲染
- 渲染分析
- core.js && babel
- core.js -- 到底是什么
- 编译器那些术语
- 词法解析 -- tokenize
- 语法解析 -- ast
- 遍历节点 -- traverser
- 转换阶段、生成阶段略
- babel
- babel -- 初步上手之了解
- babel -- 初步上手之各种配置(preset-env)
- babel -- 初步上手之各种配置@babel/helpers
- babel -- 初步上手之各种配置@babel/runtime
- babel -- 初步上手之各种配置@babel/plugin-transform-runtime
- babel -- 初步上手之各种配置(babel-polyfills )(未来)
- babel -- 初步上手之各种配置 polyfill-service
- babel -- 初步上手之各种配置(@babel/polyfill )(过去式)
- babel -- 总结
- 各种工具
- 前端 -- 工程化
- 了解 -- Yeoman
- 使用 -- Yeoman
- 了解 -- Plop
- node cli -- 开发自己的脚手架工具
- 自动化构建工具
- Gulp
- 模块化打包工具为什么出现
- 模块化打包工具(新) -- webpack
- 简单使用 -- webpack
- 了解配置 -- webpack.config.js
- webpack -- loader 浅解
- loader -- 配置css模块解析
- loader -- 图片和字体(4.x)
- loader -- 图片和字体(5.x)
- loader -- 图片优化loader
- loader -- 配置解析js/ts
- webpack -- plugins 浅解
- eslit
- plugins -- CleanWebpackPlugin(4.x)
- plugins -- CleanWebpackPlugin(5.x)
- plugin -- HtmlWebpackPlugin
- plugin -- DefinePlugin 注入全局成员
- webapck -- 模块解析配置
- webpack -- 文件指纹了解
- webpack -- 开发环境运行构建
- webpack -- 项目环境划分
- 模块化打包工具 -- webpack
- webpack -- 打包文件是个啥
- webpack -- 基础配置项用法
- webpack4.x系列学习
- webpack -- 常见loader加载器
- webpack -- 移动端px转rem处理
- 开发一个自己loader
- webpack -- plugin插件
- webpack -- 文件指纹
- webpack -- 压缩css和html构建
- webpack -- 清里构建包
- webpack -- 复制静态文件
- webpack -- 自定义插件
- wepack -- 关于静态资源内联
- webpack -- source map 对照包
- webpack -- 环境划分构建
- webpack -- 项目构建控制台输出
- webpack -- 项目分析
- webpack -- 编译提速优护体积
- 提速 -- 编译阶段
- webpack -- 项目优化
- webpack -- DefinePlugin 注入全局成员
- webpack -- 代码分割
- webpack -- 页面资源提取
- webpack -- import按需引入
- webpack -- 摇树
- webpack -- 多页面打包
- webpack -- eslint
- webpack -- srr打包后续看
- webpack -- 构建一个自己的配置后续看
- webpack -- 打包组件和基础库
- webpack -- 源码
- webpack -- 启动都做了什么
- webpack -- cli做了什么
- webpack - 5
- 模块化打包工具 -- Rollup
- 工程化搭建代码规范
- 规范化标准--Eslint
- eslint -- 扩展配置
- eslint -- 指令
- eslint -- vscode
- eslint -- 原理
- Prettier -- 格式化代码工具
- EditorConfig -- 编辑器编码风格
- 检查提交代码是否符合检查配置
- 整体流程总结
- 微前端
- single-spa
- 简单上手 -- single-spa
- 快速理解systemjs
- single-sap 不使用systemjs
- monorepo -- 工程
- Vue -- 响应式了解
- Vue2.x -- 源码分析
- 发布订阅和观察者模式
- 简单 -- 了解响应式模型(一)
- 简单 -- 了解响应式模型(二)
- 简单 --了解虚拟DOM(一)
- 简单 --了解虚拟DOM(二)
- 简单 --了解diff算法
- 简单 --了解nextick
- Snabbdom -- 理解虚拟dom和diff算法
- Snabbdom -- h函数
- Snabbdom - Vnode 函数
- Snabbdom -- init 函数
- Snabbdom -- patch 函数
- 手写 -- 虚拟dom渲染
- Vue -- minVue
- vue3.x -- 源码分析
- 分析 -- reactivity
- 好文
- grpc -- 浏览器使用gRPC
- grcp-web -- 案例
- 待续