我们前端项目经常会安装第三方npm包,随着业务的发展,自研项目中为了复用以及业务模块化也会抽象出自己的npm模块。但在研发npm过程时调试是非常麻烦的,下面就我在开发npm包时遇到的问题以及应对方案进行简单的分享。npm调试的方式总共分为以下几种:
一、修改引入路径
import xxx from 'my-npm'
const xxx = require('my-npm')
这个方案的优点在于不需要任何学习成本,我们知道当我们导入一个包时,应用会从当前目录node_modules不停向上检索寻找,直到找到为止。其实这个路径我们也可以改为本地的相对 \ 绝对路径。 例如:
import xxx from 'my-project/node_modules/my-npm/dist/index.esm.js'
或者直接修改 dependencies
"dependencies": {
"my-npm": "file:包的路径",
}
此方案缺点:很明显这个方案纯人工,而且需要频繁修改代码,容易误提交至生产,我相信一个有追求的程序员肯定不会这么干的。
二、npm link
在开发多个包时,我们需要在本地环境中使用最新的依赖版本,而无需将这些包发布到远程,npm通过软链解决了这个问题 (官方推荐调试方法)
1、开发npm包,在包所在目录执行 yarn\npm link
我这边安装的是yarn,执行yarn link命令后可以看到以下日志
MacBook-Pro my-npm % yarn link
yarn link v1.22.15
success Registered "my-npm".
info You can now run `yarn link "my-npm"` in the projects where you want to use this package and it will be used instead.
✨ Done in 0.04s.
2、在引入项目所在目录链接刚刚生成的npm链接
看到以下日志信息则表明链接成功
MacBook-Pro my-project % yarn link my-npm
yarn link v1.22.15
success Using linked package for "my-npm".
✨ Done in 0.39s.
这时在项目 my-project/node_modules
下我们可以看到依赖包my-npm有所更新
至此便可在项目中调试npm包了,如果想了解更多可以查看 官方文档,上述介绍的官方推荐的npm link的方案尽管这在许多情况下可能有效,但它通常会带来严重的限制和依赖关系解决、文件系统之间的符号链接互操作性等问题。不知道大家在开发react项目时有没有遇到这样一个现象
由于项目和npm属于不同的项目,当安装同一个依赖但版本有所不同时,就会存在多个副本,刚好这个依赖又不支持多例这时应用就会报错,更多报错原因请查看 recat 错误提示
三、更好的调试方案 - yalc
为了解决上述npm link遇到的问题,现在推荐一个更好的联调方案 yalc。yalc可以通过模拟发布npm包并将它们存放在一个特殊的全局存储中(例如位于~/.yalc
中),当你在项目中通过命令引入时会将包内容拉入当前项目的.yalc
文件目录下,并在项目根目录下创建一个特殊的yalc.lock
文件(类似yarn.lock和package.json),用来确保执行yalc例行程序时的一致性
.yalc
文件
对比npm link
可以发现少了包本身的依赖资源(node_modules)、源码,完全模拟了npm正式发布,因此不会出现依赖关系问题
yalc.lock
文件
{
"version": "v1",
"packages": {
"my-npm": {
"signature": "706c971278224bb90edd0c11855ab18e",
"file": true,
"replaced": "^0.1.3"
}
}
}
下面是详细的操作步骤:
1、安装
使用 npm:
npm i yalc -g
使用 yarn:
yarn global add yalc
2、如何使用
模拟发布(yalc publish/push)
在npm包中模拟发布,将包资源存储在全局存储中
MacBook-Pro my-npm % yalc publish
my-npm@0.1.3 published in store.
项目中引入
通过以下两种方法都可成功引入存储在全局的依赖内容,推荐方法1(不需要修改package.json)
引入方法 1
在项目中运行命令yalc link my-npm
,会将node_modules中创建指向包内容的符号链接,并且不会修改package.json中的内容
MacBook-Pro my-project % yalc link my-npm
Package my-npm@0.1.3 linked ==> /Users/Desktop/code/my-project/node_modules/my-npm
引入方法 2
在项目中运行yalc add my-npm
时,会将内容拉入当前项目根目录.yalc
下,并将 file:.yalc/my-npm
依赖关系注入到package.json中
MacBook-Pro my-project % yalc add my-npm
Package my-npm@0.1.3 added ==> /Users/Desktop/code/my-project/node_modules/my-npm
package.json
文件
"dependencies": {
"my-npm": "file:.yalc/my-npm",
// ...
}
这时我们就可以在项目中使用最新的资源了
四、应用优化
调试依赖包的问题解决了,但是我们发现了一个问题,每当我们调整依赖包逻辑时,都需要重新手动build依赖,然后重新输入命令发布,如何自动处理这部分流程减少我们人工成本呢,这里我们可以借助一个工具了nodemon
来监听文件的变化。
全局安装 yarn global add nodemon
\ npm i nodemon -g
在 my-npm
package.json中配置文件监听
"scripts": {
"publish": "yarn build && yalc push",
"watch": "nodemon --ignore dist/ --ignore node_modules/ --watch src/ -C -e js,jsx,ts,tsx,css,less --debug -x 'yarn publish'",
"build": "rollup -c"
},
配置完成后,我们只需在my-npm
路径下执行yarn watch
即可监听文件更新并同步到my-project项目中。