如何模拟一个小程序项目打包的流程
一、Uni-app 执行 yarn run dev:mp-weixin后会发生什么
(一)准备工作
- 克隆项目:创建以 typescript 开发的工程(如命令行创建失败,请直接访问 https://gitee.com/dcloud/uni-preset-vue/repository/archive/vite-ts.zip 下载模板)。
npx degit dcloudio/uni-preset-vue#vite-ts my-vue3-project
- 执行
dev:mp-weixin这个命令时,yarn或npm会运行package.json文件中定义的scripts部分的对应命令。通常会类似于这样定义:"scripts": {"dev:mp-weixin": "uni -p mp-weixin" }
(二)执行后发生的事情
- 编译项目:
uni -p mp-weixin命令会调用 uni-app 的 CLI 工具,编译你的项目代码。uni-app 会将你的 Vue.js 代码转换为微信小程序可以识别的代码,包括将.vue文件编译成微信小程序的wxml、wxss、js和json文件。 - 生成微信小程序项目文件:编译完成后,uni-app 会在项目的
dist目录下生成一个专门为微信小程序准备的项目文件夹。这个文件夹包含了所有编译好的代码和资源文件,可以直接在微信开发者工具中打开并运行。 - 监视文件变化(开发模式):如果命令是针对开发环境的(如
dev:mp-weixin),uni-app CLI 通常会启动一个开发服务器,并持续监视项目文件的变化。当你修改项目中的文件时,它会自动重新编译,并更新到dist目录中的微信小程序项目文件夹中。 - 启动开发服务器:在某些情况下,uni-app 还可能会启动一个本地开发服务器,方便在浏览器中实时预览应用的 H5 版本,并且可以同步调试。
二、实现类似 uni 插件的 vite 插件
(一)创建命令行工具
- 在项目中创建一个可以在命令行执行的工具,通常可以通过在
package.json中定义一个脚本来实现。可以使用 Node.js 创建一个 CLI 工具,并通过配置package.json来实现全局或本地运行。在package.json中定义vue-mini作为一个可执行命令,并且将bin/vue-mini.js文件链接到该命令。{"name": "vue-mini-plugin","version": "1.0.0","main": "index.js","license": "MIT","bin": {"vue-mini": "./bin/vue-mini.js"},"scripts": {"vue-mini": "vue-mini"},"dependence": {},"dependencies": {} }
(二)项目结构
![[图片]](https://i-blog.csdnimg.cn/direct/1dde4b04f5e54f78bf7c512fe9eccaae.png)
(三)编写vue-mini.js
在bin目录下创建vue-mini.js文件,这个文件会作为 CLI 工具的入口文件。
#!/usr/bin/env nodeimport { spawn } from "child_process";
import { resolve, dirname } from "path";
import { fileURLToPath } from "url";// 获取当前文件的路径
const __filename = fileURLToPath(import.meta.url);
const __dirname = dirname(__filename);// 获取 mode 参数
const mode = process.argv.includes("--mode")? process.argv[process.argv.indexOf("--mode") + 1]: "development";
console.log(`mode: ${mode}`);// 运行不同的脚本
if (mode === "development") {const devScript = resolve(__dirname, "../scripts/development.js");const childProcess = spawn("node", [devScript], {stdio: "inherit",cwd: __dirname,shell: false,});childProcess.on("exit", (code, signal) => {if (code!== 0) {console.error(`服务启动失败,退出码: ${code}`);} else {console.log(`服务正常退出`);}});
} else {console.error("无效的模式参数");
}
(四)编写development.js
在scripts目录下创建development.js文件,这个文件将负责实际的开发模式下的构建和启动过程。
import { spawn } from "child_process";
import { resolve, dirname } from "path";
import { fileURLToPath } from "url";const __filename = fileURLToPath(import.meta.url);
const __dirname = dirname(__filename);const serveScript = resolve(__dirname, "../serve.js");const childProcess = spawn("node", [serveScript], {stdio: "inherit",cwd: __dirname,shell: false,
});childProcess.on("exit", (code, signal) => {if (code!== 0) {console.error(`服务启动失败,退出码: ${code}`);} else {console.log(`服务正常退出`);}
});
(五)编写build.js
import express from "express";
import { dirname } from "path";
import { fileURLToPath } from "url";
import { mkdir, readFileSync, rm, writeFileSync } from "fs";
import { transform } from "esbuild";
import { parse } from "@vue/compiler-sfc";const __filename = fileURLToPath(import.meta.url);
const __dirname = dirname(__filename);const app = express();const port = 3000;if (process.argv.includes("--clean")) {rm(__dirname + "/dist", { recursive: true }, (err) => {if (err) console.log(err);});
}mkdir(__dirname + "/dist/index", { recursive: true }, (err) => {if (err) console.log(err);
});app.get("/", (req, res) => {res.sendFile(__dirname + "/src/index.html");
});app.get("/*.js", (req, res) => {const path = req.path;const file = readFileSync(__dirname + "/src" + path, "utf-8");writeFileSync(__dirname + "/dist/index.js", file);
});app.get("/*.css", (req, res) => {const path = req.path;const file = readFileSync(__dirname + "/src" + path, "utf-8");writeFileSync(__dirname + "/dist/index.css", file);
});app.get("/*.ts", async (req, res) => {const path = req.path;const file = readFileSync(__dirname + "/src" + path, "utf-8");const transformResult = await transform(file, {loader: "ts",format: "esm",target: "es6",});writeFileSync(__dirname + "/dist/index.js", transformResult.code);
});app.get("/*.vue", (req, res) => {const path = req.path;const fileContent = readFileSync(__dirname + "/src" + path, "utf-8");const parsed = parse(fileContent);if (parsed.descriptor.template) {writeFileSync(__dirname + "/dist/index/index.wxml",parsed.descriptor.template.content);}if (parsed.descriptor.scriptSetup) {writeFileSync(__dirname + "/dist/index/index.js",parsed.descriptor.scriptSetup.content);}if (parsed.descriptor.styles[0].content) {writeFileSync(__dirname + "/dist/index/index.wxss",parsed.descriptor.styles[0].content);}writeFileSync(__dirname + "/dist/index/index.json", "");const projectJson = readFileSync(__dirname + "/src/project.config.json","utf-8");writeFileSync(__dirname + "/dist/project.config.json", projectJson);
});app.listen(port, () => {console.log(`http://localhost:${port}`);
});
(六)安装和测试
在项目根目录下运行以下命令,确保你的 CLI 工具可以运行:
yarnyarn link
这将创建一个全局链接,允许你直接使用vue-mini命令。现在你可以测试运行以下命令:vue-mini --mode development。
得到打包的文件:

相关文章:
如何模拟一个小程序项目打包的流程
一、Uni-app 执行 yarn run dev:mp-weixin后会发生什么 (一)准备工作 克隆项目:创建以 typescript 开发的工程(如命令行创建失败,请直接访问 https://gitee.com/dcloud/uni-preset-vue/repository/archive/vite-ts.z…...
设计模式七大原则详解
设计模式七大原则详解 设计模式中的“七大原则”是面向对象编程(OOP)中的一组指导原则,这些原则帮助开发者编写灵活、可维护、可扩展的代码。这些原则并不直接等同于设计模式,但它们是设计模式的基础。下面是这七大原则ÿ…...
Navicat On-Prem Server 2.0 | MySQL与MariaDB基础管理功能正式上云
近日,Navicat 发布了 Navicat On-Prem Server 2.0 的重大版本更新。这标志着这款自2021年首发的私有云团队协作解决方案迈入了一个崭新的阶段。此次2.0版本的飞跃性升级,核心聚焦于MySQL与MariaDB基础管理功能的全面革新与强化,赋予了用户的操…...
汽车车门的美观与功能:矫平工艺的精细修复
汽车车门的美观与功能:矫平工艺的精细修复 在汽车制造的精细工艺中,车门不仅是车辆外观的重要组成部分,更是功能性的关键载体。车门的平整度直接影响到车辆的密封性、噪音控制以及整体的美观度。面对生产过程中可能出现的车门变形问题&#…...
【Python】05.Python 中的列表与元组
一、列表与元组的概念 列表是一种在代码中批量表示/保存数据的方式 元组和列表相比, 是非常相似的, 只是列表中放哪些元素可以修改调整, 元组中放的元素是创建元组的时候就设定好的, 不能修改调整 二、列表的创建 创建列表主要有两种方式. [ ] 表示一个空的列表。如果需要往…...
【Go】十五、分布式系统、Consul服务注册发现、Nacos配置中心搭建
分布式 传统开发方式的痛点: 我们的服务分为很多种:用户服务、商品服务、订单服务等,若我们一个成熟的体系内,新添加一个服务,会变得十分的繁琐与困难 当我们的负载较大时,如果选择添加机器的方式来减轻…...
[Linux#48][网络] 令牌环网 | IPv4 | socket 套接字 | TCP | UDP | 网络字节序列
目录 1.网络 1.0 令牌环网(了解) 1.1 IP 地址 1.3 网络通信的基本脉络 IPv4地址解释 2.Socket 编程预备 2.1 端口号 2.2 传输层协议 2.3 网络字节序列 库函数定义 函数说明 1.网络 1.0 令牌环网(了解) 相同令牌时&am…...
Mac OS14外接显示器字体过小和放大字体模糊问题的简单解决
文章目录 问题简述解决方法 问题简述 使用Mac mini外接2K 显示器时,默认分辨率是25601440,字体较小,如果切换成19201080,字体又变大模糊。 解决方法 使用HiDP I(一种显示技术,使用多个物理像素显示1个像…...
Python-pptx:如何在幻灯片中轻松插入与填充表格
哈喽,大家好,我是木头左! 安装和设置Python-PPTX 确保你的系统中已经安装了Python。然后,使用pip安装python-pptx库: pip install python-pptx安装完成后,你就可以开始编写脚本来操作PowerPoint文件了。 创建表格的基础步骤 使用python-pptx创建表格涉及几个关键步骤…...
ERROR 2003 (HY000): Can‘t connect to MySQL server on ‘localhost:3306‘ (10061)
ERROR 2003 (HY000): Cant connect to MySQL server on localhost:3306 (10061) mysql-8.0.30-winx64 有时候还是没启动起来的原因,不知道为什么,手动点点 mysql-8.0.30-winx64_mysql8.0.30-CSDN博客...
MySQL优化策略(大数据量)
一、 前提: 1.数据规模 : 明确数据量级是上亿级,这需要特殊的处理,比如分区、索引等策略。 2.数据增长率 : 了解数据的增加速度,有助于预估未来存储和性能需求,从而提前规划扩展策略。 3.访问模式 : 分析是读多写少…...
在Excel里制作简单游戏界面
生成随机激活码 找工具箱 插入按钮 建宏 方法一:新建按钮的时候创建宏 方法二:右键->指定宏 VBA VBA代码界面 调整字体 VBA代码 Public str As String 存储激活码显示的字符 Public st As String 中间变量,用来替代随机数 Public ot…...
火语言RPA流程组件介绍--鼠标拖拽元素
🚩【组件功能】:在开始位置上按下鼠标,拖动到结束坐标或指定元素上放下鼠标,实现目标元素的拖拽 配置预览 配置说明 丨拖动元素 支持T或# 默认FLOW输入项 开始拖动的元素,并从当前元素开始按下鼠标 丨拖动到 目标元素/目标位…...
计算机三级网络技术总结 第十一章网络管理技术
能正常接受来自路由的通知,说明路由上已设置SNMP代理并具有发出通知的功能。UDP端口号缺省为162攻击者使用无效的IP地址,利用TCP连接的三次握手过程,使得受害主机处于开放会话的请求中,直至连接超时。在此期间,受害主机…...
「豆包 Marscode 体验官」AI 加持的云端 IDE——三种方法高效开发前后端聊天交互功能
以下是「豆包 MarsCode 体验官」优秀文章,作者努力的小雨。 豆包 MarsCode 豆包MarsCode 编程助手支持的 IDE: 支持 Visual Studio Code 1.67.0 及以上版本,以及 JetBrains 系列 IDE,如 IntelliJ IDEA、Pycharm 等,版本要求为 22…...
基于Linux文件编程实现处理Excel表格的数据
目录 前言 整体的代码框架 如何读取数据文件的数据 read_line 如何处理读取到的数据 process_data 运行结果 总结 前言 本文是基于Linux文件编程的一个小实验,用文件IO来读取Excel表格的数据,处理后写入另一个文件,本文只是对文件IO的…...
make 程序规定的 makefile 文件的书写语法(2)
(13)接着开始一个更复杂的例子,课程的素材 2 ,先给出书写 makefile 的框架 : (14) (15) 谢谢...
容器化安装jenkins稳定版长期维护版本LTS
前提已有 docker-compose和docker-ce环境,这里安装稳定的Lts版本即可。 选择稳定版本 这里选择LTS 稳定长期维护的版本 在docker镜像找到LTS稳定版本 部署jenkins服务 创建持久化数据目录 jenkinsdata]# pwd /data/jenkinsdata编写docker-compose文件 jenkins_…...
如何让人工智能训练更快
影响人工智能训练时间的因素 在深度学习训练中,训练时间的计算涉及到多个因素,包括 epoch 数、全局 batch size、微 batch size、计算设备数量等。下面是一个基本的公式来说明这些参数之间的关系(注意,这只是一个基本的说明公式&…...
linux/ubuntu国内镜像安装gitleaks敏感信息扫描工具教程及避坑点
1、背景 利用gitleaks扫描git仓库或者文件 GitHub上有比较详细的教程,但是由于每个人的安装环境不同,坑很多,网上能查到的有效信息也比较少。这里就以我坑很多的环境为例,捋一下步骤。 GitHub - gitleaks/gitleaks: Protect an…...
论文解读:交大港大上海AI Lab开源论文 | 宇树机器人多姿态起立控制强化学习框架(二)
HoST框架核心实现方法详解 - 论文深度解读(第二部分) 《Learning Humanoid Standing-up Control across Diverse Postures》 系列文章: 论文深度解读 + 算法与代码分析(二) 作者机构: 上海AI Lab, 上海交通大学, 香港大学, 浙江大学, 香港中文大学 论文主题: 人形机器人…...
FastAPI 教程:从入门到实践
FastAPI 是一个现代、快速(高性能)的 Web 框架,用于构建 API,支持 Python 3.6。它基于标准 Python 类型提示,易于学习且功能强大。以下是一个完整的 FastAPI 入门教程,涵盖从环境搭建到创建并运行一个简单的…...
Cilium动手实验室: 精通之旅---20.Isovalent Enterprise for Cilium: Zero Trust Visibility
Cilium动手实验室: 精通之旅---20.Isovalent Enterprise for Cilium: Zero Trust Visibility 1. 实验室环境1.1 实验室环境1.2 小测试 2. The Endor System2.1 部署应用2.2 检查现有策略 3. Cilium 策略实体3.1 创建 allow-all 网络策略3.2 在 Hubble CLI 中验证网络策略源3.3 …...
Vue2 第一节_Vue2上手_插值表达式{{}}_访问数据和修改数据_Vue开发者工具
文章目录 1.Vue2上手-如何创建一个Vue实例,进行初始化渲染2. 插值表达式{{}}3. 访问数据和修改数据4. vue响应式5. Vue开发者工具--方便调试 1.Vue2上手-如何创建一个Vue实例,进行初始化渲染 准备容器引包创建Vue实例 new Vue()指定配置项 ->渲染数据 准备一个容器,例如: …...
Python如何给视频添加音频和字幕
在Python中,给视频添加音频和字幕可以使用电影文件处理库MoviePy和字幕处理库Subtitles。下面将详细介绍如何使用这些库来实现视频的音频和字幕添加,包括必要的代码示例和详细解释。 环境准备 在开始之前,需要安装以下Python库:…...
回溯算法学习
一、电话号码的字母组合 import java.util.ArrayList; import java.util.List;import javax.management.loading.PrivateClassLoader;public class letterCombinations {private static final String[] KEYPAD {"", //0"", //1"abc", //2"…...
AGain DB和倍数增益的关系
我在设置一款索尼CMOS芯片时,Again增益0db变化为6DB,画面的变化只有2倍DN的增益,比如10变为20。 这与dB和线性增益的关系以及传感器处理流程有关。以下是具体原因分析: 1. dB与线性增益的换算关系 6dB对应的理论线性增益应为&…...
Chromium 136 编译指南 Windows篇:depot_tools 配置与源码获取(二)
引言 工欲善其事,必先利其器。在完成了 Visual Studio 2022 和 Windows SDK 的安装后,我们即将接触到 Chromium 开发生态中最核心的工具——depot_tools。这个由 Google 精心打造的工具集,就像是连接开发者与 Chromium 庞大代码库的智能桥梁…...
Golang——7、包与接口详解
包与接口详解 1、Golang包详解1.1、Golang中包的定义和介绍1.2、Golang包管理工具go mod1.3、Golang中自定义包1.4、Golang中使用第三包1.5、init函数 2、接口详解2.1、接口的定义2.2、空接口2.3、类型断言2.4、结构体值接收者和指针接收者实现接口的区别2.5、一个结构体实现多…...
日常一水C
多态 言简意赅:就是一个对象面对同一事件时做出的不同反应 而之前的继承中说过,当子类和父类的函数名相同时,会隐藏父类的同名函数转而调用子类的同名函数,如果要调用父类的同名函数,那么就需要对父类进行引用&#…...
