🧑💻 写在开头
点赞 + 收藏 === 学会🤣🤣🤣
为什么须要版本检测
1. 办理欣赏器缓存题目
- 静态资源缓存:欣赏器会缓存 JS、CSS 等静态资源,用户大概继承利用旧版本
- 用户体验影响:用户无法及时获取新功能,导致功能缺失或操纵非常
2. 保障功能同等性
- 功能同步:确保全部效户都能利用最新的功能和修复
- 数据同等性:克制因版本差异导致的数据不同等题目
3. 提拔用户体验
- 主动提示:在新版本发布后主动关照用户更新
- 无缝升级:镌汰用户手动革新页面的需求
版本检测核心思绪
团体架构
构建阶段 → 版本文件天生 → 运行时检测 → 版本对比 → 用户提示
技能实现要点
1. 版本标识天生
- 构建时天生:每次打包时天生唯一的版本标识
- 时间戳方案:利用时间戳确保每次构建版本号唯一
2. 版本文件摆设
- JSON 格式:将版本信息生存为 version.json 文件
- 静态访问:通过 HTTP 哀求可直接访问版本文件
3. 客户端检测机制
- 定时轮询:定期查抄服务器版本文件
- 版本对比:比力当地缓存版本与服务器版本
- 智能提示:仅在版本不同等时提示用户
版本检测实现步调
步调一:构建版本文件天生脚本
创建 build-version.js 文件:- // build-version.js (自动生成版本文件脚本)
- const fs = require('fs')
- const path = require('path')
- // 方案A:使用时间戳作为版本标识(最简单,确保每次打包唯一)
- const version = new Date().getTime().toString()
- // 版本文件内容
- const versionJson = {
- version: version,
- updateTime: new Date().toLocaleString() // 可选:添加更新时间,便于排查
- }
- // 写入version.json文件(项目根目录)
- const versionPath = path.resolve(__dirname, 'public', 'version.json')
- fs.writeFileSync(versionPath, JSON.stringify(versionJson, null, 2), 'utf-8')
- console.log(`✅ 自动生成版本文件成功,版本号:${version}`)
复制代码 步调二:修改构建下令
在 package.json 中修改构建下令:- {
- "scripts": {
- "build:prod": "node build-version.js && vue-cli-service build"
- }
- }
复制代码 步调三:设置 Vue 构建过程
在 vue.config.js 中添加版本文件复制设置:- chainWebpack(config) {
- // ... 其他配置
-
- // 复制 version.json 到 dist 目录
- config.plugin('copy')
- .tap(args => {
- const hasVersionJson = args[0].some(item => item.from === 'version.json')
- if (!hasVersionJson) {
- args[0].push({
- from: path.resolve(__dirname, 'public/version.json'),
- to: path.resolve(__dirname, 'dist/version.json')
- })
- }
- return args
- })
- }
复制代码 步调四:实现版本检测工具类
创建 src/utils/versionUpdate.js:- // src/utils/versionUpdate.js
- import { Notification } from 'element-ui'
- /**
- * 版本更新检测工具类(仅生产环境启用轮询,内置环境判断)
- */
- class VersionUpdate {
- constructor(options = {}) {
- this.config = {
- versionFileUrl: '/version.json', // 版本文件地址
- localVersionKey: 'cmpVersion', // 本地存储的版本号key
- disableFetchCache: true, // 禁用Fetch缓存
- pollInterval: 5 * 60 * 1000, // 5分钟轮询一次
- hasNotified: false // 是否已提醒过用户有新版本
- }
- Object.assign(this.config, options)
- // 定时轮询定时器
- this.pollTimer = null
- // 识别当前环境(Vue CLI 4 自动注入的环境变量)
- this.isProduction = process.env.NODE_ENV === 'production'
- }
- /**
- * 核心方法:执行版本检测
- */
- async checkVersion(isInit = false) {
- try {
- if (this.config.hasNotified) return false
- const localVersion = localStorage.getItem(this.config.localVersionKey) || ''
- const fetchOptions = {}
- if (this.config.disableFetchCache) {
- fetchOptions.cache = 'no-cache'
- }
- const response = await fetch(this.config.versionFileUrl, fetchOptions)
- if (!response.ok) {
- throw new Error(`版本文件请求失败,状态码:${response.status}`)
- }
- const latestVersionInfo = await response.json()
- const serverVersion = latestVersionInfo.version
- if (isInit) {
- this.cacheLatestVersion(serverVersion)
- return true
- }
- if (serverVersion && serverVersion !== localVersion) {
- this.config.hasNotified = true
- console.log('有新版本可用', latestVersionInfo)
- Notification({
- title: '🎉 有新版本可用',
- dangerouslyUseHTMLString: true,
- message: `<p >建议点击刷新页面,以获取最新功能和修复</p> <p >更新时间:${latestVersionInfo.updateTime}</p>`,
- duration: 0,
- customClass: 'check-version-notify',
- onClick: () => {
- this.forceRefreshPage()
- },
- onClose: () => {
- this.resetNotifyFlag()
- }
- })
- return true
- } else {
- // 版本一致时,重置提醒标记,便于后续轮询检测新版本
- this.config.hasNotified = false
- // console.log('当前已是最新版本,已缓存最新版本号')
- return false
- }
- } catch (error) {
- console.warn('版本检测异常,不影响应用运行:', error.message)
- return false
- }
- }
- /**
- * 启动定时轮询检测(内置环境判断:仅生产环境生效)
- */
- async startPolling() {
- // 核心:非生产环境,直接返回,不启动轮询
- if (!this.isProduction) {
- console.log('当前为非生产环境,不启动版本检测轮询')
- return
- }
- // 生产环境:正常启动轮询
- this.stopPolling() // 先停止已有轮询,避免重复启动
- this.checkVersion(true) // 立即执行一次检测
- this.pollTimer = setInterval(() => {
- this.checkVersion()
- }, this.config.pollInterval)
- console.log(`生产环境版本轮询检测已启动,每隔${this.config.pollInterval / 1000 / 60}分钟检测一次`)
- }
- /**
- * 停止定时轮询检测
- */
- stopPolling() {
- if (this.pollTimer) {
- clearInterval(this.pollTimer)
- this.pollTimer = null
- console.log('版本轮询检测已停止')
- }
- }
- /**
- * 重置提醒标记
- */
- resetNotifyFlag() {
- this.config.hasNotified = false
- }
- // 缓存最新版本号
- cacheLatestVersion(version) {
- localStorage.setItem(this.config.localVersionKey, version)
- this.resetNotifyFlag()
- }
- // 强制刷新页面
- forceRefreshPage() {
- window.location.reload(true)
- }
- }
- const versionUpdateInstance = new VersionUpdate()
- export { VersionUpdate, versionUpdateInstance }
- export default versionUpdateInstance
复制代码 创建自界说.check-version-notify的版本检测全局样式:
- // 版本检测通知样式
- .check-version-notify{
- border: 3px solid transparent !important;
- cursor: pointer;
- background-color: rgba(255, 255, 255, 0.6) !important;
- backdrop-filter: blur(5px);
- &:hover{
- border: 3px solid $--color-primary !important;
- }
- .el-notification__icon{
- font-size: 18px;
- height: 18px;
- }
- .el-notification__title{
- font-size: 14px;
- line-height: 18px;
- }
- .el-notification__group{
- margin-left: 8px;
- }
- }
复制代码 步调五:在应用入口启动版本检测
在 App.vue 或符合的入口文件中启动版本检测:- import versionUpdate from '@/utils/versionUpdate'
- ...
- mounted() {
- versionUpdate.startPolling()
- },
- beforeDestroy() {
- versionUpdate.stopPolling()
- }
复制代码 如果对您有所资助,欢迎您点个关注,我会定时更新技能文档,各人一起讨论学习,一起进步。
免责声明:如果侵犯了您的权益,请联系站长及时删除侵权内容,谢谢合作!qidao123.com:ToB企服之家,中国第一个企服评测及软件市场,开放入驻,技术点评得现金. |