炒菜式手把手教学:基本的memorepo项目npm发包流程

·  阅读 166

菜的由来

由于vite2.0发布,想尝试一下vite在项目中运用,所以出于对项目构建的想法,想实现一个比较前沿的vue脚手架功能,当然,还是基于vite做的,不过这里分享的是比较基本的memorepo实现的一个基本的脚手架功能。本文所分享的内容会尽量基本,代码也会尽量少,主要讲讲怎么实现和所遇到的一些坑,下面我们开始吧!!(开发过程中遇到的坑点下面都有标注)

我们需要的厨房

  • 我们的灶:nodejs环境

  • 厨房基本设施:lerna(全局安装一下),yarn,npm

下面我们开始一步一步做吧!!

准备我们的锅碗瓢盆

首先我们需要装食材的盆子,先用lerna去生成最基本的目录结构,lerna不是很了解的可以去看看大佬们的文章

lerna init --independent
复制代码

目录结构

├─lerna.json
├─package.json
├─packages
复制代码

然后我们下面开始创建一个packages下面的包,名为cli,这里我将package.json的name,命名为@mvtest/cli,这种scope命名方式也是根据vue-cli源码模仿的,也是符合memorepo的概念。

lerna create cli
复制代码

生成的目录如下

├─lerna.json
├─package.json
├─packages
|    ├─cli
|    |  ├─README.md
|    |  ├─package.json
|    |  ├─lib
|    |  |  └cli.js
|    |  ├─__tests__
|    |  |     └cli.test.js
复制代码

到此,最基本的memorepo目录结构就生成了。

下面我们在多创建一个demo项目目录用于测试使用,目录结构如下,为了使测试项目能够正常的使用脚手架的本地调试功能,我使用了vite创建了一个基本的项目(vite-project)。现在的目录结构如下:

├─example
|    ├─vite-project
|    |      ├─.gitignore
|    |      ├─index.html
|    |      ├─package.json
|    |      ├─vite.config.js
|    |      ├─src
|    |      |  ├─App.vue
|    |      |  ├─main.js
|    |      |  ├─components
|    |      |  |     └HelloWorld.vue
|    |      |  ├─assets
|    |      |  |   └logo.png
|    |      ├─public
|    |      |   └favicon.ico
├─lerna.json
├─package.json
├─packages
|    ├─cli
|    |  ├─README.md
|    |  ├─package.json
|    |  ├─lib
|    |  |  └cli.js
|    |  ├─__tests__
|    |  |     └cli.test.js
复制代码

现在开始将packages里面的包在vite-project项目里做本地调试,首先我们该怎么连接呢?很简单,只要在vite-project的package.json里面加上,workspaces和private属性

  // vite-project/package.json
  "private": "true",
  "workspaces": [
     "../../packages/*"
  ],
复制代码

然后yarn一下,vite-project项目里面的node_modules就会将packages的包做成映射安装到node_modules,旁边会多个小尖头,类似电脑上快捷键的意思,映射到packages下面的某个包。这里之所以是@mvtest/cli,是因为上面讲到的cli包的package.json里面的name属性命名成了这样,所以这里会以@mvtest作为一个当前包目录,然后将cli包放在该目录下面

image.png

坑点1:

有人问,这里如果不写private可不可以?那我们来去除一下private看看

image.png 结果报错了,后来我去百度了一下,看到官方的解释如下:

workspace仅仅是为了你的本机方便维护依赖。当你的包被发布到npm的时候,npm完全没有workspace的概念。所以为了避免你手抖发出去。yarn强制你把启用了workspace的工程的标记为私有。

现在所有的锅碗瓢盆已经准备好了,下面我们开始做基本的菜吧!

没啥做的,先做个焖土豆吧!!

为了能够使用自定义的命令,我们需要给我们菜起个名字,mtd(焖土豆的菜名),现在cli的package.json里面加一个bin命令,

  // package.json
  "bin": {
    "mtd": "lib/cli.js"
  },
复制代码

指定的运行文件是lib/cli.js,那么我们现在里面写一句代码。

// packages/cli/lib/cli.js
#!/usr/bin/env node

console.log('hello mtd!!');
复制代码

这里的#!/usr/bin/env node是必须要的,是告诉脚本当前执行的环境。

然后我们将vite-project的node_modules删除,重新yarn,这时候的node_modules的.bin目录里面会多个mtd命令,这正是我们所想要的,这里的mtd就是映射上面配置的bin属性

image.png

下面我们开始试下该命令,在vite-project的package.json,新增一个scripts,start命令

// vite-project/package.json
  "scripts": {
    "dev": "vite",
    "build": "vite build",
    "serve": "vite preview",
    "start": "mtd" //刚加的命令
  }
复制代码

我们运行一下npm run start

image.png 哈哈!不出所料,成功打印了!焖土豆味道还可以,感觉自己好牛逼!!

焖土豆好了,准备上桌吧!!

菜好了,上桌吧!

菜好了,我们准备上菜,上菜有两种方式:

  • 手动式:npm publish

    正常的npm包发布,但是需要每次cd到packages里面,感觉很麻烦。

  • 智能式:lerna publish

    无需进入到packages里面一个一个发包,只需要在项目跟目录运行就行啦,一次运行,发所有,而且只会发packages下面修改过的包。毫无疑问,聪明的人都会选这种!!

结果,上菜上了半天,我也是醉了!!

坑点2

我们开始运行下lerna publish看看

image.png 出乎意料,结果报错了?上面的意思好像需要我提交代码才可以发布,好吧,我就先提交代码,然后再次publish

image.png

结果还是出错,不过这个不用担心,只是外网的问题,github导致有时候可以访问,有时候不可以访问,所以我们只要重新publish就行啦。

image.png 这时候会出现发布选项,这里我选了alpha版本, 结果,郁闷了~~~

坑点3 image.png

好吧,说我需要本地npm登录一下,那我就登录一下

npm login
复制代码

然后会出现

image.png 完事之后继续发包

坑点4

结果发完了,告诉我success了,但是始终没在我的主页找到我发的包,后来网上搜了很久才知道,跟git有关,lerna publish的时候,已经打了tag,所以不会在发布到npm上,所以再次运行的时候需要运行lerna publish from-git,这时候lerna publish的时候不会再需要选版本号了,还是发的之前的版本。 还有一种方法是运行lerna publish from-package,会把当前所有本地包中的package.json和远端npm比对,如果是npm上不存在的包版本,都执行一次npm publish

运行lerna publish from-git我们继续发包

image.png

还是不行!!已自闭!

坑点5

这里需要设置发的包的publishConfig属性,如下:

// packages/cli/package.json
  "publishConfig": {
    "access": "public"
  },
复制代码

因为加了private属性的原因,有人问,直接去掉private不就行了,但是为了方便改来改去,还是直接加上上面的属性更直接点。

再次运行,终于可以发到npm官网上了,哈哈哈!!

但是不要高兴的太早,还有一个需要注意的地方!!

坑点6

因为发的包格式是@**/**,被称为scope包,所以发这个包之前需要在npm上建一个组织

image.png

比如我这个包是@mvtest/cli,那我就创建一个@mvtest这个组织,最后发包也是会发到这个组织下面,不然发包还是会报404报错,永远发不上去!!

image.png 切记,切记,切记!!重要的说三遍!!!

好了,菜终于上完了,下面就等客人们吃了,直接npm install @mvtest/cli即可。

总结

以前没有用memorepo方式写的时候,感觉写个脚手架很简单,用了这个,虽然说整个概念上有所先进,但是踩了不少的坑,因此,跟大家分享下,希望对大家有所帮助!!!源码在这,后面会将该demo和vite结合实现一个基本的脚手架功能,持续关注哦!!

分类:
前端
标签: