miniapp-upload 小程序本地上传发布工具
小程序开发会经历几个阶段:
- 本地开发
- 上传开发版(设置体验版)测试
- 提交审核
- 发布
本文档主要聚焦在第二步: 上传代码。众所周知。小程序上传代码可以通过微信开发者工具
(以下简称开发工具)中的上传
功能将代码上传至微信公众平台中。大部分时候这完全没问题。那么本篇文章到此为止(才怪)。
有些经验的开发者会发现这种模式有那么一丢丢问题。就是每次上传都需要打开微信开发者工具(好像没什么问题?)
那如果现在有一种方式。我的构建上传并不需要打开微信开发者工具。只需要通过命令行发布呢?
没错。微信官方通过开发工具
提供了一个CLI工具来实现这个。
前置条件
在使用这个特性前。你需要自查一下本机环境
安装微信开发者工具,并完成扫码登录
微信开发者工具开启端口。【开发工具】-【设置】-【安全设置】-【服务端口】
[可选]如果你是Windows用户.在项目根目录创建
pub-weapp.config.private.json
,并填入cli路径bash{ "windowsWeiXinCliPath": "C:\\Program Files (x86)\\Tencent\\微信web开发者工具\\cli.bat" }
注意:这里填写你电脑上实际的工具位置
添加命令配置
添加依赖
bash
pnpm add -wD inquirer@^8.0.0 shelljs@^0.8.5
在项目根目录packages.json
中。新建打包命令
json
"scripts": {
// 其他命令...
"mini:uat": "node scripts/pub-weapp --target uat",
"mini:prd": "node scripts/pub-weapp --target prd",
},
在项目根目录创建上传脚本scripts/pub-weapp.js
输入以下命令
js
const os = require('os')
const path = require('path')
const fs = require('fs')
const shelljs = require('shelljs')
// const chalk = require('chalk')
const inquirer = require('inquirer')
const argv = require('minimist')(process.argv.slice(2))
const target = argv.target || 'uat'
const isMac = os.type() === 'Darwin'
const isWindows = os.type() === 'Windows_NT'
const isSupportSystem = isMac || isWindows
const configFileName = 'pub-weapp.config.private.json'
const uploadVersion = {
uat: argv.v || '1.0.0',
stg: argv.v || '1.0.0',
prd: argv.v
}[target]
const packageOptions = [
{
name: 'taro-shop-component',
},
]
const chalk = {
red: (text = '') => `\x1B[31m${text}\x1B[0m`,
green: (text = '') => `\x1B[32m${text}\x1B[0m`,
yellow: (text = '') => `\x1B[33m${text}\x1B[0m`
}
// 配置文件不存在则手动创建
if (isWindows && !fs.existsSync(path.join(__dirname, '../', configFileName))) {
console.log(
` ${chalk.yellow(
'警告'
)}: 由于 Windows 首次使用发布命令,将为您创建配置文件,请在工程根目录 ${configFileName} 中填入您的【微信开发工具安装路径】,填写完成后再重新执行命令即可`
)
fs.writeFileSync(path.join(__dirname, '../', configFileName), `{ "windowsWeiXinCliPath": "这是示例示例 D:/软件/微信web开发者工具/cli.bat" }`)
return
}
inquirer
.prompt([
{
type: 'checkbox',
message: `即将打包 ${target} 环境,回车选择 package`,
name: 'packageNameList',
choices: packageOptions.map((item) => item.name)
}
])
.then(
({
/** 本次打包的 包名 */
packageNameList
}) => {
const successList = []
const failList = []
packageNameList.forEach((packageName) => {
const option = packageOptions.find((item) => item.name === packageName)
run(packageName, option, () => {
successList.push(packageName)
})
})
// 全部发布完成后,检查哪些没发布成功
packageNameList.forEach((packageName) => {
const isSuccess = successList.indexOf(packageName) !== -1
!isSuccess && failList.push(packageName)
})
console.log(' ')
console.log(' ')
console.log(` ${chalk.green('批量发布完成')}: ${new Date().toLocaleTimeString()}`)
console.log(` 发布:${packageNameList.length} ${packageNameList.join('、')}`)
console.log(` 成功:${chalk.green(successList.length)} ${successList.join('、')}`)
console.log(` 失败:${chalk.red(failList.length)} ${failList.join('、')}`)
function run(packageName = '', option = {}, onSuccessCallback) {
/** 小程序包目录 */
const weappDir = `packages/${packageName}`
/** 打包命令 */
const buildCmd = `pnpm build:${target}:weapp`
/** 用于发布的 打包输出目录 */
// const outputDir = projectConfigJson.miniprogramRoot.replace(/\//g, '')
const pubDir = 'dist/weapp'
const pubFullDir = path.join(process.cwd(), 'packages', packageName, pubDir)
// 自定义命令语句
if (option.cmd) {
shelljs.exec(option.cmd, { cwd: process.cwd() })
onSuccessCallback()
return
}
/** 微信开发工具命令行所在路径 */
let cli = ''
if (isMac) {
cli = '/Applications/wechatwebdevtools.app/Contents/MacOS/cli'
} else {
const pubWeappConfig = require('../pub-weapp.config.private.json')
cli = validateWeiXinCliPath(pubWeappConfig.windowsWeiXinCliPath)
}
if (!isSupportSystem) {
return console.log(`${chalk.red('【错误】')} 该命令仅支持 Mac 与 Windows 使用,不支持 ${os.type()}`)
}
if (!cli) {
return console.log(`${chalk.red('【错误】')} 请根据 docs/开始.md 在根目录配置 ${scriptConfigFileName} 文件,或检查配置文件中指向的 cli 文件是否存在`)
}
if (target === 'prod' && !uploadVersion) {
return console.log(`${chalk.red('【错误】')} 生产环境,请输入版本号参数 【--v=x.x.x】`)
}
shelljs.exec(buildCmd, {
cwd: path.join(process.cwd(), weappDir)
})
console.log(' ')
console.log(' ')
console.log(` ${chalk.green('打包完成,开始上传')}`)
console.log(' ')
console.log(' ')
console.log(` 发布参数 ====================================================`)
console.log(' ')
console.log(` ${chalk.green('cli')}: ${cli}`)
console.log(` ${chalk.green('发布源文件')}: ${pubFullDir}`)
console.log(` ${chalk.green('uploadVersion')}: ${uploadVersion}`)
console.log(` ${chalk.green('desc')}: ${target}`)
console.log(' ')
cliLogin(cli)
shellExec(cli, `upload --project ${pubFullDir} -v ${uploadVersion} -d '${target}'`)
console.log(` ${chalk.green('发布完成')}: ${packageName} ${new Date().toLocaleTimeString()}`)
onSuccessCallback()
}
}
)
/** 校验微信开发者工具安装路径 */
function validateWeiXinCliPath(cliPath = '') {
if (!cliPath) {
throw Error('请在项目根目录 package.json [windowsWeiXinCliPath] 填入你的 windows 电脑【微信开发者工具】的完整安装路径')
}
const exist = fs.existsSync(cliPath)
if (!exist) {
throw Error(`${cliPath} 文件不存在`)
}
if (!/cli\.bat/.test(cliPath)) {
throw Error('weiXinCliPath 字段不合法,应为 <完整安装路径>/cli.bat')
}
return cliPath
}
function cliLogin(cli) {
try {
// 修复文件夹包含中文
if (isWindows) {
shelljs.exec(`chcp 65001`)
}
const res = shellExec(cli, 'islogin').stdout
const isLogin = JSON.parse(res).login
if (!isLogin) {
console.log(` ${chalk.yellow('警告')}: 尚未登录微信开发工具,请扫码登录`)
shellExec(cli, 'login')
}
} catch (error) {
console.log(` ${chalk.red('警告')}: 登录微信开发工具失败,请打开新的微信开发工具登录后重试,或联系发布脚本的开发人员`)
console.error(error)
process.exit(1)
}
}
function shellExec(cliPath, command) {
const innerCommand = isWindows ? `cli.bat ${command}` : `${cliPath} ${command}`
return shelljs.exec(
innerCommand,
isWindows
? {
cwd: path.dirname(cliPath)
}
: {}
)
}
打包上传
运行打包命令. 会执行上传操作。
bash
pnpm mini:prd
如果配置成功。会执行成功。如果失败。请查看具体报错信息。或联系架构部解决