2025盛夏版:基于electron37+vite7的Vue桌面客户端保姆教程

Electron是一个基于Chromium和Node.js,可以使用HTML、CSS和JavaScript构建跨平台应用的技术框架,兼容Mac、Windows和 Linux。虽然B/S是目前开发的主流,但是C/S仍然有很大的市场需求。受限于浏览器的沙盒限制,网页应用无法满足某些场景下的使用需求,而桌面应用可以方便地读写本地文件、发起跨域请求、调用更多系统资源,再加上Web开发低成本、高效率的优势,这种方式越来越受到开发者的喜爱。

2023年10月,我发布了《2023金秋版:基于electron-vite构建React桌面客户端》。当时的electron-vite还是1.x版本,如今已经发布了4.x版本,适配了Vite7,开发体验也更加完善。在省去了手动融合Electron和Vite繁琐过程的同时,还实现了V8字节码、主进程和预加载脚本热更新等非常实用的功能,要比自己从头搭建容易得多。

相比本系列教程的2023金秋版,本教程2025盛夏版将采用全新的Demo案例,通过开发一个批量图片压缩的实用小工具,全面掌握桌面客户端开发所涉及的各个知识点,新增了集成Chrome插件、检查更新、优化控制台输出、macOS签名等多个细节内容。经过本教程的学习,你将掌握更全面的Electron实战开发技能。希望能够帮助各位省去摸索的时间,少走弯路,快速完成实际工作中的项目开发。React技术栈的小伙伴不要错过哟!

本教程也同步推出《2025金秋版:基于electron37+vite7的React桌面客户端保姆教程》,欢迎Vue技术栈的小伙伴来阅读。

先睹为快

先看下目录了解本教程都有哪些内容。

章节目录

dart 复制代码
1 Electron核心概念
• 1.1 主进程(main)
• 1.2 渲染进程(renderer)
• 1.3 预加载脚本(preload)
2 初始化项目
• 2.1 配置npm国内镜像源
• 2.2 使用electron-vite新建项目
• 2.3 精简项目
• 2.4 去掉renderer的src目录
• 2.5 ESLint相关配置(选读)
• 2.6 设置DevTools快捷键
3 Vite基础配置
• 3.1 支持Sass/Scss/Less/Stylus
• 3.2 设置路径别名
4 项目架构搭建
• 4.1 项目目录结构设计
• 4.2 关于样式命名规范
• 4.3 设置全局公用样式
5 引入Element Plus
• 5.1 安装Element Plus
• 5.2 设置Element Plus为中文语言
6 渲染进程页面开发
• 6.1 构建Login页面
• 6.2 构建Home页面
• 6.3 允许Electron跨域请求和加载本地资源
• 6.4 构建公共Header组件
• 6.5 构建页面路由
• 6.6 构建框架页面Entry
• 6.7 引入路由
• 6.8 路由跳转:Login页面跳转Home页面
• 6.9 路由守卫
• 6.10 路由跳转:退出返回登录页
7 主进程与渲染进程通信方式一:暴露electronAPI给渲染进程
• 7.1 预加载脚本(preload)
• 7.2 构建"关于软件"弹窗
8 主进程与渲染进程通信方式二:send与on/once
• 8.1 预加载脚本(preload)开发
• 8.2 主进程开发:读取目录中的全部图片文件
• 8.3 继续渲染进程Home页面开发
• 8.4 运行效果
• 8.5 解决windows系统主进程控制台中文乱码的问题
• 8.6 实现系统控制台多彩文字色输出
• 8.7 实现设置输出目录
• 8.8 关于ipcRenderer.on/once
9 主进程与渲染进程通信方式三:invoke与handle
• 9.1 实现主进程图片压缩处理
• 9.2 使用invoke与handle串通渲染进程与主进程
• 9.3 为什么不使用send与on/once
10 其他Electron常用配置
• 10.1 设置应用图标
• 10.2 设置APP窗口大小
• 10.3 禁止生产环境的DevTools
• 10.4 集成Chrome插件
• 10.5 禁止启动同个Electron应用
11 build项目
• 11.1 Electron相关镜像源配置(无需更改)
• 11.2 设置build版应用icon
• 11.3 配置macOS的签名
• 11.3.1 无签名版应用(可安装,但不能自动更新)
• 11.3.2 有签名版应用(可安装,可自动更新)
• 11.4 设置不需要打包的目录
• 11.5 执行build命令
• 11.6 build后的目录结构
• 11.7 设置windows安装包允许用户自定义安装目录
• 11.8 设置windows安装包强制安装路径(选读)
• 11.8.1 全局安装(C:\Program Files)
• 11.8.2 指定默认目录安装
12 自动更新
• 12.1 部署更新服务器
• 12.2 实现主进程检查更新的逻辑
• 12.3 设置更新服务器地址的几种方式
• 12.3.1 主进程 autoUpdater.setFeedURL(推荐)
• 12.3.2 electron-builder.yml(不使用)
• 12.3.3 dev-app-update.yml(不使用)
• 12.4 在渲染进程实现静默检查更新和自动下载
• 12.5 在渲染进程实现手动检查更新和手动下载
13 其他说明
• 13.1 源代码保护
• 13.2 敏感字符串保护
• 13.3 主进程热更新(选读)
• 13.4 批量升级全部项目npm依赖包
• 13.5 项目的不足之处
14 项目Git源码
结束语

主要依赖包版本

本教程的主要依赖包版本:

复制代码
Node.js 22.17.1
electron 37.2.3
electron-builder 26.0.12
electron-vite 4.0.0
electron-updater 6.6.2
eslint 9.31.0
vue 3.5.18
vue-router 4.5.1
vite 7.0.5
element-plus 2.10.4
sharp 0.34.3

※注:

代码区域每行开头的:

"+" 表示新增

"-" 表示删除

"M" 表示修改

跟着教程操作一遍,就可以快速上手Electron开发啦!下面请跟着新版教程一步步操作。

最终成品预览

1 Electron核心概念

学习Electron最先要掌握的就是它的主进程与渲染进程概念。网上很多相关教程也进行了详细介绍,又是画关系图又是文字描述的。这里只想把最核心的内容总结一下,以最简单最通俗的方式让各位迅速理解。

掌握三个核心概念即可:

1.1 主进程(main)

每个Electron应用都有一个单一的主进程,作为应用程序的入口点。主进程运行在Node.js环境,因此可以使用Node.js的所有API能力。主进程并不在浏览器环境中运行,因此不进行页面渲染。

1.2 渲染进程(renderer)

渲染进程说白了就是平时的Web页面前端开发。每个Electron应用都会为每个打开的BrowserWindow生成一个单独的渲染器进程。但是渲染进程是无法直接调用Node.js的API的。

1.3 预加载脚本(preload)

为了让渲染进程与主进程进行通信从而形成一个整体,预加载脚本的作用就是它们之间的桥梁。预加载脚本属于渲染进程的范畴,与渲染进程共享同一个全局window,因此可以通过window来传递数据。但并不是简单地通过给window添加属性就能使用,以下方式是无法把preload.js共享给渲染进程使用的:

javascript 复制代码
// 预加载脚本(preload.js)
window.myAPI = {
  desktop: true
}

// 渲染进程
console.log(window.myAPI)
// => undefined(获取不到)

这是因为Electron的语境隔离(Context Isolation),使得预加载脚本与渲染进程的主要运行环境是隔离的,以避免将任何API都加入到渲染进程的网页中。

因此,需要使用contextBridge来安全地实现交互:

javascript 复制代码
// 预加载脚本(preload.js)
const { contextBridge } = require('electron')

contextBridge.exposeInMainWorld('myAPI', {
  desktop: true
})


// 渲染进程
console.log(window.myAPI)
// => { desktop: true } (成功获取)

以上方式就是通过contextBridge.exposeInMainWorld将preload.js中的myAPI数据共享给渲染进程的网页使用。

官网详细介绍:

www.electronjs.org/zh/docs/lat...

2 初始化项目

2.1 配置npm国内镜像源

npm默认是从国外源站拉取依赖包的,为提高下载速度和稳定性,建议配置为国内镜像源。

执行:

arduino 复制代码
npm config set registry https://registry.npmmirror.com

执行后,可以通过以下命令查看npm配置,确认是否设置成功:

arduino 复制代码
npm config list

输出的内容中,检查registry的值是否已改为国内镜像源地址:

ini 复制代码
registry = "https://registry.npmmirror.com/"

2.2 使用electron-vite新建项目

找个合适的目录,执行项目创建命令:

sql 复制代码
npm create @quick-start/electron@latest

执行后,会要求填写项目名称,这里我填写的是electron-vite-vue-app,可根据情况自定。

yaml 复制代码
? Project name: electron-vite-vue-app

然后,会要求选择框架,选择vue:

css 复制代码
? Select a framework:
    vanilla
>   vue
    react
    svelte
    solid

最后是几个配置选项:

yaml 复制代码
? Add TypeScript? >> No 
是否使用TypeScript?选No,本教程使用JavaScript。如果喜欢TypeScript,请选择Yes。
? Add Electron updater plugin? >> Yes 
是否添加Electron updater插件?选择Yes。
? Enable Electron download mirror proxy? >> Yes
是否开启Electron镜像下载代理。在国内网络环境,强烈建议选择Yes。

项目创建完成后,执行以下命令:

bash 复制代码
cd electron-vite-vue-app
npm install

安装完成后,执行启动命令:

arduino 复制代码
npm run dev

运行效果如下:

2.3 精简项目

接下来,删除用不到的目录和文件,最简化项目。

bash 复制代码
    ├─ /.vscode
    ├─ /build
    ├─ /node_modules
    ├─ /out
    ├─ /resources
    ├─ /src
    |  ├─ /main
    |  ├─ /preload
    |  ├─ /renderer
    |  |  ├─ /src
-   |  |  |  ├─ /assets
    |  |  |  ├─ /components
-   |  |  |  |  └─ Versions.vue
    |  |  |  ├─ App.vue
    |  |  |  └─ main.js
    |  |  └─ index.html
    ├─ .editorconfig
    ├─ .gitignore
    ├─ .npmrc
    ├─ .prettierignore
    ├─ .prettierrc.yaml
    ├─ dev-app-update.yml
    ├─ electron-builder.yml
    ├─ electron.vite.config.js
    ├─ eslint.config.mjs
    ├─ package-lock.json
    ├─ package.json
    └─ README.md

2.4 去掉renderer的src目录

以上项目结构有两个src目录,容易混淆,而且路径表达也略显啰嗦。可以把 src/renderer/src 目录里的文件放到 src/renderer 目录中,然后删除 src/renderer/src 目录。

调整后的renderer目录如下:

bash 复制代码
...(略)
|  ├─ /renderer
|  |  ├─ /components
|  |  ├─ App.vue
|  |  ├─ index.html
|  |  └─ main.js
...(略)

以上文件删除后,页面会报错。这是因为相应的文件引用已不存在。需要继续修改代码,先让项目正常运行起来。

逐个修改以下文件,最终精简代码依次如下:

src/renderer/App.vue

xml 复制代码
<script setup></script>

<template>
  <div class="App">Electron-Vite-Vue-App</div>
</template>

<style scoped></style>

src/renderer/main.js

javascript 复制代码
import { createApp } from 'vue'
import App from './App.vue'

createApp(App).mount('#app')

src/renderer/index.html

xml 复制代码
<!doctype html>
<html>
  <head>
    <meta charset="UTF-8" />
    <title>图片压缩小工具</title>
    <meta
      http-equiv="Content-Security-Policy"
      content="default-src 'self'; script-src 'self'; style-src 'self' 'unsafe-inline'; img-src 'self' data:"
    />
  </head>

  <body>
    <div id="app"></div>
    <script type="module" src="./main.js"></script>
  </body>
</html>

在windows环境中,src/renderer/index.html<title>内容将显示在客户端窗口标题栏中。

执行:

arduino 复制代码
npm run dev

运行效果如下:

2.5 ESLint相关配置(选读)

默认的ESLint和prettier配置基本可以满足大部分场景。

可以根据自己的开发习惯进行配置。

例如,我个人习惯缩进为4个空格,这样的缩进会让代码稍微松散一些。

还有一些其他的格式化习惯,统一修改在prettier配置文件中(供参考)。

修改 .prettierrc.yaml

yaml 复制代码
# JavaScript中的代码使用单引号(')代替双引号(")
singleQuote: true
# 每行代码末尾不加分号
semi: false
# 每行代码最大长度100个字符,超出时 Prettier 会自动换行
printWidth: 100
# 对象、数组、函数参数列表等结构中,最后一项不加逗号。
trailingComma: none
# 缩进时使用 4 个空格
tabWidth: 4
# 使用空格进行缩进,而不是 Tab 字符。确保不同编辑器显示一致。
useTabs: false
# 自动检测操作系统使用的换行符(Linux 是 \n,Windows 是 \r\n)。适用于跨平台开发,避免换行符冲突。
endOfLine: auto

但是,完成以上配置后,对代码进行格式化,ESLint就会提示有不合规的格式。

例如,prettier设置为4个空格缩进,但ESLint提示要2个空格缩进:

这是因为在一个项目中同时使用ESLint和Prettier时,两者对代码格式有不同的规则从而导致冲突。

有代码洁癖的话,这就不能忍。需要解决它。

最简单的办法就是关闭掉ESlint对Prettier格式的检测。

修改 eslint.config.mjs

javascript 复制代码
    import eslintConfig from '@electron-toolkit/eslint-config'
M   //import eslintConfigPrettier from '@electron-toolkit/eslint-config-prettier'
    import eslintPluginVue from 'eslint-plugin-vue'
    import vueParser from 'vue-eslint-parser'
    
    export default [
        ...(略)
		{
            files: ['**/*.{js,jsx,vue}'],
            rules: {
                'vue/require-default-prop': 'off',
                'vue/multi-word-component-names': 'off',
+               'prettier/prettier': ['error', { tabWidth: 4 }]
            }
        },
M       // eslintConfigPrettier
    ]

注释掉eslintConfigPrettier,并且设定与prettier统一的4个空格缩进即可。

经过以上设置,就可以治愈代码洁癖强迫症了。

2.6 设置DevTools快捷键

Chrome的调试工具在是开发中必不可少的利器。默认情况下,Electron是没有鼠标右键的。打开DevTools的默认方式为:

windows快捷键:Shift+Ctrl+I(英文字母"艾")

macOS快捷键:Command+Option+I(英文字母"艾")

也可以自定义设置快捷键。

修改 src/main/index.js

javascript 复制代码
-   import { app, shell, BrowserWindow, ipcMain } from 'electron'
+   import { app, shell, BrowserWindow, ipcMain, globalShortcut } from 'electron'
    ...(略)
    
    function createWindow() {
        ...(略)
    
        // HMR for renderer base on electron-vite cli.
        // Load the remote URL for development or the local html file for production.
        if (is.dev && process.env['ELECTRON_RENDERER_URL']) {
            mainWindow.loadURL(process.env['ELECTRON_RENDERER_URL'])
        } else {
            mainWindow.loadFile(join(__dirname, '../renderer/index.html'))
        }
    
+       // 设置DevTools快捷键
+       globalShortcut.register('CommandOrControl+Shift+i', function () {
+           mainWindow.webContents.openDevTools()
+       })
    }
    
    ...(略)

经过以上设置,DevTools打开方法为:

windows快捷键:Ctrl+Shift+I (与默认一致)

macOS快捷键:Command+Shift+I (默认的Option换成了Shift)

当然,之前默认的DevTools打开快捷键仍然生效。

3 Vite基础配置

3.1 支持Sass/Scss/Less/Stylus

Vite本身提供了对.scss/.sass/.less/.styl/.stylus文件的内置支持。无需再安装特定的Vite插件,但必须安装相应的预处理器依赖。

支持Sass/Scss,执行以下命令:

复制代码
npm install -D sass

支持Less,执行以下命令:

复制代码
npm install -D less

支持Stylus,执行以下命令:

复制代码
npm install -D stylus

安装后,就可以直接使用以上对应的CSS预处理语言了,非常方便。

CSS预处理Vite官方说明:

cn.vitejs.dev/guide/featu...

3.2 设置路径别名

electron-vite已经预设了路径别名配置。

例如:src/renderer/App.vue,可以直接省略成 @renderer/App.vue

由于本教程已经删除了src/renderer/src目录,因此需要修改对应的预设配置。

修改 electron.vite.config.mjs

css 复制代码
    ...(略)
    renderer: {
        resolve: {
            alias: {
-               '@renderer': resolve('src/renderer/src')
+               '@renderer': resolve('src/renderer')
            }
        },
        plugins: [vue()]
    }
    ...(略)

4 项目架构搭建

4.1 项目目录结构设计

项目目录结构可根据项目实际灵活制定。这里分享下我常用的结构。重点是renderer目录的结构设计,主要分为公用模块目录、组件模块目录、页面模块目录、路由配置目录等几个部分,让项目结构更加清晰合理。

❤️❤️❤️------试读结束------❤️❤️❤️

后续精彩章节

dart 复制代码
• 4.1 项目目录结构设计
• 4.2 关于样式命名规范
• 4.3 设置全局公用样式
5 引入Element Plus
• 5.1 安装Element Plus
• 5.2 设置Element Plus为中文语言
6 渲染进程页面开发
• 6.1 构建Login页面
• 6.2 构建Home页面
• 6.3 允许Electron跨域请求和加载本地资源
• 6.4 构建公共Header组件
• 6.5 构建页面路由
• 6.6 构建框架页面Entry
• 6.7 引入路由
• 6.8 路由跳转:Login页面跳转Home页面
• 6.9 路由守卫
• 6.10 路由跳转:退出返回登录页
7 主进程与渲染进程通信方式一:暴露electronAPI给渲染进程
• 7.1 预加载脚本(preload)
• 7.2 构建"关于软件"弹窗
8 主进程与渲染进程通信方式二:send与on/once
• 8.1 预加载脚本(preload)开发
• 8.2 主进程开发:读取目录中的全部图片文件
• 8.3 继续渲染进程Home页面开发
• 8.4 运行效果
• 8.5 解决windows系统主进程控制台中文乱码的问题
• 8.6 实现系统控制台多彩文字色输出
• 8.7 实现设置输出目录
• 8.8 关于ipcRenderer.on/once
9 主进程与渲染进程通信方式三:invoke与handle
• 9.1 实现主进程图片压缩处理
• 9.2 使用invoke与handle串通渲染进程与主进程
• 9.3 为什么不使用send与on/once
10 其他Electron常用配置
• 10.1 设置应用图标
• 10.2 设置APP窗口大小
• 10.3 禁止生产环境的DevTools
• 10.4 集成Chrome插件
• 10.5 禁止启动同个Electron应用
11 build项目
• 11.1 Electron相关镜像源配置(无需更改)
• 11.2 设置build版应用icon
• 11.3 配置macOS的签名
• 11.3.1 无签名版应用(可安装,但不能自动更新)
• 11.3.2 有签名版应用(可安装,可自动更新)
• 11.4 设置不需要打包的目录
• 11.5 执行build命令
• 11.6 build后的目录结构
• 11.7 设置windows安装包允许用户自定义安装目录
• 11.8 设置windows安装包强制安装路径(选读)
• 11.8.1 全局安装(C:\Program Files)
• 11.8.2 指定默认目录安装
12 自动更新
• 12.1 部署更新服务器
• 12.2 实现主进程检查更新的逻辑
• 12.3 设置更新服务器地址的几种方式
• 12.3.1 主进程 autoUpdater.setFeedURL(推荐)
• 12.3.2 electron-builder.yml(不使用)
• 12.3.3 dev-app-update.yml(不使用)
• 12.4 在渲染进程实现静默检查更新和自动下载
• 12.5 在渲染进程实现手动检查更新和手动下载
13 其他说明
• 13.1 源代码保护
• 13.2 敏感字符串保护
• 13.3 主进程热更新(选读)
• 13.4 批量升级全部项目npm依赖包
• 13.5 项目的不足之处
14 项目Git源码
结束语

阅读完整版

📖 完整教程可订阅我的公众号【卧梅又闻花

《2025盛夏版:基于electron37+vite7的Vue桌面客户端保姆教程(上篇)》

《2025盛夏版:基于electron37+vite7的Vue桌面客户端保姆教程(下篇)》

项目Git源码

本项目已上传至Gitee和GitHub,方便各位下载。

Gitee:

gitee.com/betaq/elect...
Github:

github.com/Yuezi32/ele...

相关推荐
洛千陨13 分钟前
Web Worker基础概念 & 图片滤镜处理实际应用 -- Vue3
javascript·vue.js
半花15 分钟前
【vue】v-自定义指令
前端·vue.js
武昌库里写JAVA22 分钟前
【MySQL】MySQL数据库如何改名
java·vue.js·spring boot·sql·学习
牛马喜喜1 小时前
electron-vite 动态加载脚本 实现动态插件
electron·node.js
飞翔的佩奇2 小时前
Java项目:基于SSM框架实现的社区团购管理系统【ssm+B/S架构+源码+数据库+毕业论文+答辩PPT+远程部署】
java·数据库·vue.js·毕业设计·mybatis·答辩ppt·社区团购
_未完待续2 小时前
框架实战指南-错误处理
前端·vue.js
_未完待续2 小时前
框架实战指南-组件参考
前端·vue.js
半花2 小时前
【Vue】通信组件
前端·vue.js
前端 贾公子2 小时前
vue如何在data里使用this
前端·javascript·vue.js
_未完待续3 小时前
框架实战指南-元素参考
前端·vue.js