开启掘金成长之旅!这是我参与「掘金日新计划 · 2 月更文挑战」的第 10 天,点击查看活动详情
前言
今天我们来完成脚手架启动阶段需要完成的一些任务,就是启动阶段需要做的一些检查
core函数
我们先来写一下core函数的模板
core/cli/lib/index.js
"use strict";
const log = require("@wson-koa2-cli/log");
// 命令启动前的检查
function prepare() {
}
function cli() {
try {
// 命令启动前的检查
prepare();
} catch (error) {
log.error(error);
}
}
module.exports = cli;
这样只要prepare里面只要有报错的话,错误信息都会被抓去住,并且不会在向下执行
检查node版本号
why do the node version check?
因为我们用到了node新版本的api,如果用户是低版本的话,运行脚手架会报错。所以需要提醒用户升级到最新版本的node
semver 库
Semver是一个专门分析Semantic Version(语义化版本)的工具,“semver”其实就是这两个单词的缩写。Npm使用了该工具来处理版本相关的工作。
semver可以作为一个node模块,同时也可以作为一个命令行工具。功能包括:
- 比较两个版本号的大小
- 验证某个版本号是否合法
- 提取版本号,例如从“=v1.2.1”体取出"1.2.1"
- 分析版本号是否属于某个范围或符合一系列条件
在此处我们用来检查用户本地的版本号是否小于我们规定的版本号
const semver = require("semver");
const LOWEST_NODE_VERSION = "12.0.0";
// 检查node的版本号
function checkNodeVersion() {
// 因为脚手架执行时就是一个node进程,所以可以从process拿到node版本号
const currentVersion = process.version;
const lowestVersion = LOWEST_NODE_VERSION;
// 通过semver这个库来比对版本号的大小
if (!semver.gte(currentVersion, lowestVersion)) {
throw new Error(
// 当前node版本小于指定版本,请升级版本
log.info(`The node version is less than ${LOWEST_NODE_VERSION}, please upgrade the node version`)
);
}
}
检查当前包是否是最新版本
const pkg = require("../package.json");
// 检测package.json版本是否小于最低版本
function checkPkgVersion() {
const currentPkgVersion = pkg.version;
if (!semver.gte(currentPkgVersion, LOWEST_PKG_VERSION)) {
throw new Error(
`imooc-ws-cli-dev suggest that your current version should greater than v${LOWEST_PKG_VERSION}, Please upgrade you version`
);
} else {
log.info("cli", currentPkgVersion);
}
}
提醒用户可升级到最新版本
这个函数要写的内容比较多,那么我们在util中新建一个包
lerna create @wson-koa2-cli/get-npm-info utils
在utils/get-npm-info/lib/index.js中写
获取数据源函数
function getDefaultRegistry(isOriginal = false) {
// 默认是从淘宝源的仓库获取
return isOriginal
? 'https://registry.npmjs.org'
: 'https://registry.npmmirror.com'
}
获取npm信息
// 获取npm信息
function getNpmInfo(npmName) {
if (!npmName) {
return null;
}
const registryUrl = getDefaultRegistry();
const npmInfoUrl = `${registryUrl}/${npmName}`;
return axios
.get(npmInfoUrl)
.then((res) => {
if (res.status === 200) {
return res.data;
} else {
return null;
}
})
.catch((err) => {
throw new Error(err);
});
}
获取包所有版本
// 全部采用async/await的写法
async function getNpmVersions(npmName) {
const data = await getNpmInfo(npmName)
if (data) {
return Object.keys(data.versions)
} else {
return []
}
}
获取比本地版本大的版本列表
// 获取比当前脚手架版本大的版本信息
function getSemverVersions(baseVersion, versions) {
return versions
.filter(version =>
// semver.satisfies函数表示获取大于^1.0.4的版本,^有大于等于的意思
semver.satisfies(version, `^${baseVersion}`)
)
// 有可能从npm上获取的版本不是排序之后的
.sort((a, b) => {
if (semver.gt(b, a)) {
return 1
} else {
return -1
}
})
}
获取包最新版本
// 获取最新版本
async function getNpmSemverVersions(baseVersion, npmName) {
const versions = await getNpmVersions(npmName)
const newVersions = getSemverVersions(baseVersion, versions)
if (newVersions && newVersions.length > 0) {
return newVersions[0]
}
}
上面函数实现了以后
在core/cli/lib/index.js中写
// 提示更新到最新版本
async function npmUpdateLatestVersionWarning() {
const currentVersion = pkg.version;
const npmName = pkg.name;
const lastVersion = await getNpmLatestVersions(currentVersion, npmName);
if (lastVersion && semver.gt(lastVersion, currentVersion)) {
log.warn(
`Please update manually ${npmName},The latest version is ${lastVersion},Update command:npm install -g ${npmName}`
);
}
}
在测试这个功能的时候一定要先发布包