基于Spring的Uniapp自动更新实现方法

ops/2024/10/19 1:28:00/

Uniapp自动更新

   本文介绍了基于rouyi-uniapp的更新包版本自动推送更新。结合minio和网址下载地址两种方式,计算版本号大小后,可选是否强制更新。

一、表结构和后端版本号检测设计

1、版本更新控制表结构

主要字段和设计思路:

fileUrl:直接下载地址,用于网址直接下载,uniapp可直接访问(isUrlDownload=”Y“)

filePath:minio下载地址, 存储minio文件管理系统表的关键字,uniapp走本地minio文件下载地址(isUrlDownload=”N“)

version:版本号3位,eg:4.0.1,与uniapp的manifest.Json的versionName对应。

versionValue:版本号值,类似于二进制值转化,在更新版本时,比价用户当前版本信息和发布的有效最高版本号,如果当前版本号低于发布的最高版本号,进行更新提示。

Eg:Version=4.0.1; versionValue = 1*Math.power(10,0)+0*Math.power(10,1)+1*Math.power(10,2)。平方基数值不得小于10,否则值计算的最终大小会不符合。

isUrlDownload:是否使用直接地址下载还是minio,更加灵活

Status:版本是否可用。‘Y’为可用,即使用户安装的是旧版本,也可以不更新。‘N’为版本停用,如果用户当前安装的版本状态为停用,则强制更新到最新版(状态为‘Y’,且版本号值最高)

package com.inspur.factory.factoryAppManage.domain;import java.util.Date;
import com.fasterxml.jackson.annotation.JsonFormat;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import com.inspur.common.annotation.Excel;
import com.inspur.common.core.domain.BaseEntity;
import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;/*** app版本管理对象 factory_app_manage**/
@TableName("factory_app_manage")@Data
public class FactoryAppManage extends BaseEntity
{private static final long serialVersionUID = 1L;/** 主键 */@TableIdprivate Long id;/** 版本号名称 */@Excel(name = "版本号名称")private String version;/** 版本号值 */@Excel(name = "版本号值")private Long versionValue;/** 手机品牌 */@Excel(name = "手机品牌")private String phoneBrand;/** 文件名(安装包名称) */@Excel(name = "文件名(安装包名称)")private String fileName;/** 安装包地址 */@Excel(name = "安装包地址")private String filePath;/** 下载地址 */@Excel(name = "下载地址")private String fileUrl;/** 上传时间 */
//    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")@Excel(name = "上传时间", width = 30, dateFormat = "yyyy-MM-dd")private Date fileTime;/** 状态 */@Excel(name = "状态")private String status;/** 更新说明 */@Excel(name = "更新说明")private String upgradeDescription;/** 文件大小 */@Excel(name = "文件大小")private String fileSize;/** 使用临时地址 */@Excel(name = "使用临时地址",readConverterExp = "Y=是,N=否")private String isUrlDownload;}@Overridepublic String toString() {return new ToStringBuilder(this, ToStringStyle.MULTI_LINE_STYLE).append("id", getId()).append("version", getVersion()).append("versionValue", getVersionValue()).append("phoneBrand", getPhoneBrand()).append("fileName", getFileName()).append("filePath", getFilePath()).append("fileUrl", getFileUrl()).append("fileTime", getFileTime()).append("status", getStatus()).append("upgradeDescription", getUpgradeDescription()).append("fileSize", getFileSize()).append("createTime", getCreateTime()).append("createBy", getCreateBy()).append("updateTime", getUpdateTime()).append("updateBy", getUpdateBy()).append("remark", getRemark()).toString();}
}

2、检查版本更新

    检查用户当前的版本是否可用。‘Y’为可用,即使用户安装的是旧版本,也可以不更新。‘N’为版本停用,如果用户当前安装的版本状态为停用,则强制更新到最新版(状态为‘Y’,且版本号值最高)。

//获取应当安装的app版本@Override
public FactoryAppManage getAppVersion(FactoryAppManage factoryAppManage){//传入版本号、手机系统类型List<FactoryAppManage> oldVersion = factoryAppManageMapper.selectFactoryAppManageList(factoryAppManage);if(oldVersion!=null && oldVersion.size()!=0){//如果当前版本还可使用,返回当前版本if(oldVersion.get(0).getStatus().equals("Y")){return oldVersion.get(0);}else{//如果当前版本不可使用强制更新,返回最新版本FactoryAppManage factoryAppManageQuery = new FactoryAppManage();factoryAppManageQuery.setStatus("Y");factoryAppManageQuery.setPhoneBrand(factoryAppManage.getPhoneBrand());List<FactoryAppManage> newVersion = factoryAppManageMapper.selectFactoryAppManageList(factoryAppManageQuery);if(newVersion!=null){return newVersion.get(0);}}}return null;
}

二、前端uniapp设计

版本号比较后,更新包安装提示弹窗,点击确认下载文件。

文件下载和打开主要方法如下:

1、主要应用技术

(1)直接地址下载:

uni.saveFile({})

(2)Minio下载:

Url为本地接口地址

plus.downloader.createDownload(url, {})plus.io.convertLocalFileSystemURLplus.runtime.openFile(d.filename); //选择软件打开文件

(3)H5平台下载:

主要用于电脑调试,BLOB转化,具体不做解释

(4)软件信息获取

uni.getSystemInfoSync()获取:phoneBrand(版本)version(版本号)

2、实现方法(***重点***)

App.vue根组件,每次打开任何页面都会执行到,在此文件下检测版本和更新包安装。

(1)版本检测

当前版本号为参数,后台请求对比最新版本号(版本号值最大为最新版本),返回应当安装的版本。

如果需要更新,则弹窗显示,点击确定进行安装。

根据web前台配置的是否用直接地址下载,进入安装包下载安装。

      checkUploadVersion(){//检测更新let server = config.baseUrl +'/factory/factoryAppManage/getAppVersion'; //检查更新地址(minio检测地址)let info = uni.getSystemInfoSync()uni.request({url: server,data: {phoneBrand: info.platform,version: info.appVersion},success: (res) => {if (res.data.data.version != info.appVersion) {// if (1) {let upgradeDescription = res.data.data.upgradeDescriptionuni.showModal({ //提醒用户更新title: "更新提示",content: '版本更新内容:'+ upgradeDescription,showCancel:false,success: (e) => {if (e.confirm) {if(info.uniPlatform=='web'){//h5平台调用后端minio接口下载this.downloadApp2(res.data.data)}else if(info.platform!='windows' && info.uniPlatform!='web' && res.data.data.isUrlDownload == 'Y'){//app手机端使用临时地址下载this.downloadApp1(res.data.data)}else if(info.platform!='windows' && info.uniPlatform!='web' && res.data.data.isUrlDownload == 'N'){//app手机端调用后端minio接口下载this.downloadApp3(res.data.data)}}}})}}})},

(2) minio下载

此方式具有参考意义,可以不用购买云空间存放安装包文件,直接使用minio文件存储。


   

   /** app安装包下载-(下载方式3-APP调用后端minio下载接口下载)*/downloadApp3(appVersionInfo) {var url = config.baseUrl +'/fileManage/downloadFile'+'?filePath=' + appVersionInfo.filePath+'&fileName=' + appVersionInfo.fileName; //请求下载接口地址var name = appVersionInfo.fileName;// console.log('method', reqMethod)uni.showLoading({title: '正在下载'});
// 本地路径开头使用file://,跟上手机文件本地目录storage/emulated/0,
// 这时用户文件管理器能看到的了,之后创建 京唐港app 作为文件夹,let dtask = plus.downloader.createDownload(url, {filename: "file://storage/emulated/0/京唐港app/" + name //利用保存路径,实现下载文件的重命名},(d, status)=> {//d为下载的文件对象if (status == 200) {uni.hideLoading();uni.showToast({icon: 'none',mask: true,title: '已保存到文件夹:/京唐港app/' + name, //保存路径duration: 3000,});//下载成功,d.filename是文件在保存在本地的相对路径,使用下面的API可转为平台绝对路径let fileSaveUrl = plus.io.convertLocalFileSystemURL(d.filename);setTimeout(()=>{plus.runtime.openFile(d.filename); //选择软件打开文件},1500)} else {//下载失败uni.hideLoading();plus.downloader.clear(); //清除下载任务uni.showToast({icon:'none',mask:true,title: '下载失败,请稍后重试',});}})dtask.start();},

(3)直接地址下载

此方式需要云空间

  

    /** app安装包下载-(下载方式1-APP指定url下载)*/downloadApp1(appVersionInfo){//下载方式1:指定url下载let downloadUrl = appVersionInfo.fileUrl// let downloadUrl = 'https://mp-fdbd529e-1d38-4f4a-bf37-72ba880de14a.cdn.bspapp.com/cloudstorage/00b0e017-b375-4758-88c8-4acfab810d7a.apk'uni.downloadFile({url: downloadUrl,
/*          data:{filePath:'mnQ0lCrayctz3TkHxB4rB0PeVTD7fbXNhULFZo4g+iPK0KXkzzzYJWCIJ5vxfiu1a8fzsYOb07weXbcXd92dkw==',fileName: '3.jpg'},method: 'POST',*/success: (res) => {console.log('downloadFile success, res is', res)//文件保存到本地uni.saveFile({tempFilePath: res.tempFilePath, //临时路径success: function(re) {uni.showToast({icon: 'none',mask: true,title: '文件已保存:' + re.savedFilePath, //保存路径duration: 3000,});setTimeout(() => {//打开查看uni.openDocument({filePath: re.savedFilePath,success: function(res) {// console.log('打开成功');}});}, 3000)}});uni.hideLoading();},fail: (err) => {console.log('downloadFile fail, err is:', err)uni.hideLoading();}})},

(4) H5平台电脑端下载

      /** app安装包下载-(下载方式2-h5平台web使用后端minio后端接口下载)*/downloadApp2(appVersionInfo){//下载方式2:请求接口下载let server = config.baseUrl +'/fileManage/downloadFile'+'?filePath=' + appVersionInfo.filePath+'&fileName=' + appVersionInfo.fileName; //请求下载接口地址uni.request({url: server,method: 'post',success: (res) => {/** h5 平台下载*/try {// const res = await exportOrderById({ id });//获取返回的二进制数据const blob = new Blob([res.data]); // 通过返回的流数据 手动构建blob 流const reader = new FileReader();reader.readAsDataURL(blob); // 转换为base64,可以直接放入a标签的hrefreader.onload = (e) => {// 转换完成,创建一个a标签用于下载const a = document.createElement("a");a.download = appVersionInfo.fileName; // 构建 下载的文件名称以及下载的文件格式(可通过传值输入)if (typeof e.target.result === "string") {a.href = e.target.result;}a.click();};} catch (err) {this.$message.error("遇到错误!");}}})},

三、前端web设计

1、版本页面展示

<template><div class="app-container"><el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch" label-width="90px" style="margin-bottom: 5px"><div class="con-container"><div class="lab-container"><label class="condition-item-title">版本号名称</label><el-form-item label="" prop="version" class="custom-el-form-item"><el-inputv-model="queryParams.version" class="query-param"placeholder="请输入版本号名称"clearablesize="small"@keyup.enter.native="handleQuery"/></el-form-item></div><div class="btn-container"><el-form-item><el-button type="primary" icon="el-icon-setting" size="mini" @click="conditionToggle">高级查询</el-button><el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery">搜索</el-button><el-button type="primary" icon="el-icon-refresh" size="mini" @click="resetQuery">重置</el-button><el-button type="primary" icon="el-icon-plus" size="mini" @click="handleAdd"v-hasPermi="['factory:factoryAppManage:add']">新增</el-button><el-button type="primary" icon="el-icon-download" size="mini" @click="handleExport"v-hasPermi="['factory:factoryAppManage:export']">导出</el-button><el-button type="primary" icon="el-icon-delete" size="mini" :disabled="multiple" @click="handleDelete"v-hasPermi="['factory:factoryAppManage:remove']">删除</el-button></el-form-item></div></div><div class="toggle-container" ref="toggle-container" style="display: none;"><div class="condition-item"><label class="condition-item-title">手机品牌</label><el-form-item label="" prop="phoneBrand"><el-inputv-model="queryParams.phoneBrand"placeholder="请输入手机品牌"clearablesize="small" class="query-param"@keyup.enter.native="handleQuery"/></el-form-item></div><div class="condition-item"><label class="condition-item-title">状态</label><el-form-item label="" prop="status"><el-select v-model="queryParams.status" placeholder="请选择状态" clearable size="small" class="query-param"><el-optionv-for="item in statusOptions":key="item.value":label="item.label":value="item.value"/></el-select></el-form-item></div></div></el-form><el-table v-loading="loading" ref="table" border:height="tableHeight" :header-cell-style="{fontSize:'14px', fontWeight:'500'}":data="factoryAppManageList" @selection-change="handleSelectionChange"><el-table-column type="selection" width="55" align="center" /><el-table-column label="序号" type="index" width="60" align="left"><template slot-scope="scope"><span>{{(queryParams.pageNum - 1) * queryParams.pageSize + scope.$index + 1}}</span></template></el-table-column>
<!--      <el-table-column label="主键" align="center" prop="id" />--><el-table-column label="手机品牌" align="center" prop="phoneBrand"><template slot-scope="scope"><dict-tag :options="dict.type.phone_brand" :value="scope.row.phoneBrand"/></template></el-table-column><el-table-column label="版本号名称" align="center" prop="version" /><el-table-column label="版本号值" align="center" prop="versionValue" /><el-table-column label="安装包名称" :show-overflow-tooltip="true" align="center" prop="fileName" /><el-table-column label="安装包地址" :show-overflow-tooltip="true" align="center" prop="filePath" />
<!--      <el-table-column label="下载地址" align="center" prop="fileUrl" />--><el-table-column label="上传时间" align="center" prop="fileTime" width="180"><template slot-scope="scope"><span>{{ parseTime(scope.row.fileTime) }}</span></template></el-table-column><el-table-column label="状态" align="center" prop="status"><template slot-scope="scope"><el-tag type="warning" v-if="scope.row.status=='N'">停用</el-tag><el-tag type="success" v-if="scope.row.status=='Y'">启用</el-tag></template></el-table-column>
<!--      <el-table-column label="更新说明" align="center" prop="upgradeDescription" />--><el-table-column label="文件大小(MB)" align="center" prop="fileSize" />
<!--      <el-table-column label="备注" align="center" prop="remark" />--><el-table-column label="操作" min-width="200" align="center" class-name="small-padding fixed-width"><template slot-scope="scope"><el-buttonsize="mini"type="text"icon="el-icon-download"@click="handleDownload(scope.row.filePath,scope.row.fileName)">下载</el-button><el-buttonsize="mini"type="text"icon="el-icon-tickets"@click="handleView(scope.row)"v-hasPermi="['factory:factoryAppManage:query']">详情</el-button><el-buttonsize="mini"type="text"icon="el-icon-edit"@click="handleUpdate(scope.row)"v-hasPermi="['factory:factoryAppManage:edit']">修改</el-button><el-buttonsize="mini"type="text"icon="el-icon-delete"@click="handleDelete(scope.row)"v-hasPermi="['factory:factoryAppManage:remove']">删除</el-button></template></el-table-column></el-table><paginationv-show="total>0":total="total":page.sync="queryParams.pageNum":limit.sync="queryParams.pageSize"@pagination="getList"/><!-- 添加或修改app版本管理对话框 --><el-dialog :visible.sync="open" @opened="openDialog"><div slot="title"><span>{{ title }}</span></div><div class="factoryAppManage-body"></div><el-form ref="form" :model="form" :rules="rules" label-width="120px"><div class="sub-project"><div class="sub-title"><div class="sub-title-name">app版本管理信息</div></div><div class="sub-body"><el-row><el-col :span="8" v-if="!readOnly"><el-form-item label="安装包"><up-record @sendRecordData="getRecordData"></up-record></el-form-item></el-col><el-col :span="8"><el-form-item label="上传时间" prop="fileTime" v-show="!readOnly"><el-date-picker clearable size="small"v-model="form.fileTime"type="date"value-format="yyyy-MM-dd"disabledstyle="width:100%"placeholder="选择上传时间"></el-date-picker></el-form-item><el-form-item label="上传时间:" prop="fileTime" v-show="readOnly" class="custom-form-item">{{form.fileTime}}</el-form-item></el-col><el-col :span="8"><el-form-item label="手机品牌" prop="phoneBrand" v-show="!readOnly"><el-select v-model="form.phoneBrand" placeholder="请选择手机品牌" class="custom-form-item"><el-optionv-for="dict in dict.type.phone_brand":key="dict.value":label="dict.label":value="dict.value"></el-option></el-select></el-form-item><el-form-item label="手机品牌:" prop="phoneBrand" v-show="readOnly" class="custom-form-item">{{form.phoneBrand}}</el-form-item></el-col><el-col :span="12"><el-form-item label="安装包名称" prop="fileName" v-show="!readOnly"><el-input v-model="form.fileName" placeholder="安装包名称" class="form-item" disabled/></el-form-item><el-form-item label="安装包名称:" prop="fileName" v-show="readOnly" class="custom-form-item">{{form.fileName}}</el-form-item></el-col><el-col :span="12"><el-form-item label="安装包地址" prop="filePath" v-show="!readOnly"><el-input v-model="form.filePath" placeholder="请输入安装包地址" class="form-item" disabled/></el-form-item><el-form-item label="安装包地址:" prop="filePath" v-show="readOnly" class="custom-form-item">{{form.filePath}}</el-form-item></el-col><el-col :span="8"><el-form-item label="版本号名称" prop="version" v-show="!readOnly"><el-input v-model="form.version" placeholder="四位,如(4.0.0.0)" class="form-item"/></el-form-item><el-form-item label="版本号名称:" prop="version" v-show="readOnly" class="custom-form-item">{{form.version}}</el-form-item></el-col><el-col :span="8"><el-form-item label="版本号值" prop="versionValue" v-show="!readOnly"><div v-if="!versionValueShow" @click="generateVersionValue" style="align-items: center"><el-link type="primary">计算版本号值</el-link></div><el-input v-model="form.versionValue" placeholder="请输入版本号值" disabled class="form-item" v-if="versionValueShow"/></el-form-item><el-form-item label="版本号值:" prop="versionValue" v-show="readOnly" class="custom-form-item">{{form.versionValue}}</el-form-item></el-col><el-col :span="8"><el-form-item label="直接下载地址" prop="fileUrl" v-show="!readOnly"><el-input v-model="form.fileUrl" placeholder="请输入下载地址" class="form-item"/></el-form-item><el-form-item label="直接下载地址:" prop="fileUrl" v-show="readOnly" class="custom-form-item">{{form.fileUrl}}</el-form-item></el-col><el-col :span="24"><el-form-item label="更新说明" prop="upgradeDescription" v-show="!readOnly"><el-input type="textarea" :autosize="{ minRows: 4, maxRows: 4 }" v-model="form.upgradeDescription" placeholder="请输入更新说明" maxlength="85" show-word-limit class="form-item"/></el-form-item><el-form-item label="更新说明:" prop="upgradeDescription" v-show="readOnly" class="custom-form-item">{{form.upgradeDescription}}</el-form-item></el-col><el-col :span="24"><el-form-item label="状态" v-if="!readOnly"><el-radio-group v-model="form.status" class="form-item"><el-radiov-for="dict in statusOptions":key="dict.value":label="dict.value">{{ dict.label }}</el-radio></el-radio-group></el-form-item><el-form-item label="状态" v-if="readOnly"><el-tag type="warning" v-if="form.status=='N'">停用</el-tag><el-tag type="success" v-if="form.status=='Y'">启用</el-tag></el-form-item></el-col></el-row></div></div></el-form><div slot="footer" class="dialog-footer"><el-button type="primary" @click="submitForm" v-show="!readOnly">确 定</el-button><el-button @click="cancel">取 消</el-button></div></el-dialog></div>
</template><script>
import { listFactoryAppManage, getFactoryAppManage, countFactoryAppManage, delFactoryAppManage, addFactoryAppManage, updateFactoryAppManage, exportFactoryAppManage } from "@/api/factory/factoryAppManage";
import upRecord from "@/components/FileUpload/upRecord";
import $ from 'jquery'
import selectSingleDevice from "@/components/esis/selectSingleDevice";
import {addFactoryDeviceFile} from "@/api/factory/factoryDeviceFile";
export default {name: "FactoryAppManage",dicts: ['phone_brand'],components: {upRecord},data() {// 唯一字段校验const validateUnique = (comment, rule, value, callback) => {let param = {}value =  value.trim()if (!value || value.length === 0) {callback(new Error(comment + "不能为空"));return;}this.$set(param, rule.field, value)let id =  this.form.idif(!id){ // 新增唯一校验countFactoryAppManage(param).then(res => {if(res.code === 200){if(res.data > 0){callback(new Error(comment + "已存在"));}else{callback()}}else{callback()}})}else { // 修改唯一校验this.$set(param, "id", id)countFactoryAppManage(param).then(res => {if(res.code === 200){if(res.data > 0){callback(new Error(comment + "已存在"));}else{callback()}}else{callback()}})}};return {// 遮罩层loading: true,// 导出遮罩层exportLoading: false,// 选中数组ids: [],// 非单个禁用single: true,// 非多个禁用multiple: true,// 显示搜索条件showSearch: true,versionValueShow: false,// 总条数total: 0,tableHeight: 450,// app版本管理表格数据factoryAppManageList: [],recordFileSucc: [],statusOptions:[{value:'Y',label: '启用'},{value:'N',label: '停用'}],// 弹出层标题title: "",// 是否显示弹出层open: false,//查看按钮默认不能编辑readOnly: false,// 查询参数queryParams: {pageNum: 1,pageSize: 10,version: null,versionValue: null,phoneBrand: null,fileName: null,filePath: null,fileUrl: null,fileTime: null,status: null,upgradeDescription: null,fileSize: null,},// 表单参数form: {},// 表单校验rules: {}};},watch: {'$store.state.app.screenHeight': function() { //监听屏幕高度变化if (this.$refs.table.$el.offsetTop) {this.tableHeight = window.innerHeight - this.$refs.table.$el.offsetTop - 160} else {this.tableHeight = window.innerHeight - 62 - 160}this.openDialog()}},created() {this.getList();},methods: {openDialog() {$('.factoryAppManage-body').css('top', 0).css('overflow-y', 'auto')},generateVersionValue(){debuggerlet dotVal = this.form.version.split('.')this.form.versionValue = 4*Number(dotVal[0]) + 3*Number(dotVal[1])+ 2*Number(dotVal[2])+ 1*Number(dotVal[3])this.versionValueShow = true},/** 查询app版本管理列表 */getList() {this.loading = true;listFactoryAppManage(this.queryParams).then(response => {this.factoryAppManageList = response.rows;this.total = response.total;this.loading = false;});},/** 文件下载处理*/getRecordData(val) {this.recordFileSucc = valthis.form.fileName = val[0].appendixNamethis.form.filePath = val[0].appendixPaththis.form.fileTime = new Date()this.form.createBy = val[0].createBythis.form.fileSize = val[0].fileSize.toFixed(2)},conditionToggle() {if(this.$refs['toggle-container'].style.display === 'none'){this.$refs['toggle-container'].style.display = 'inline-block';this.tableHeight = window.innerHeight - this.$refs.table.$el.offsetTop -  160}else{this.$refs['toggle-container'].style.display = 'none';this.tableHeight = window.innerHeight - this.$refs.table.$el.offsetTop -  160}},// 取消按钮cancel() {this.open = false;this.reset();},// 表单重置reset() {this.form = {id: null,version: null,versionValue: null,phoneBrand: null,fileName: null,filePath: null,fileUrl: null,fileTime: null,status: "Y",upgradeDescription: null,fileSize: null,createTime: null,createBy: null,updateTime: null,updateBy: null,remark: null};this.resetForm("form");},/** 搜索按钮操作 */handleQuery() {this.queryParams.pageNum = 1;this.getList();},/** 重置按钮操作 */resetQuery() {this.resetForm("queryForm");this.handleQuery();},// 多选框选中数据handleSelectionChange(selection) {this.ids = selection.map(item => item.id)this.single = selection.length!==1this.multiple = !selection.length},/** 新增按钮操作 */handleAdd() {this.reset();this.recordFileSucc = []this.open = true;this.readOnly = falsethis.title = "添加";},/** 修改按钮操作 */handleUpdate(row) {this.reset();const id = row.id || this.idsgetFactoryAppManage(id).then(response => {this.form = response.data;this.open = true;this.readOnly = falsethis.title = "修改";});},//下载按钮操作handleDownload(url,name){// window.location.href = process.env.VUE_APP_BASE_API + '/fileManage/downloadFile?url=' + url + '&name=' + namethis.$minio.downloadFile(url,name)},/** 详情按钮操作 */handleView(row) {this.reset();const id = row.id || this.idsgetFactoryAppManage(id).then(response => {this.form = response.data;this.open = true;this.readOnly = truethis.title = "详情";});},/** 提交按钮 */submitForm() {this.$refs["form"].validate(valid => {if (valid) {if (this.form.id != null) {updateFactoryAppManage(this.form).then(response => {this.msgSuccess("修改成功");this.open = false;this.getList();});} else {this.recordFileSucc.filter(res => {let obj = {version: this.form.version,versionValue: this.form.versionValue,phoneBrand: this.form.phoneBrand,fileName: res.appendixName,filePath: res.appendixPath,status: this.form.status,upgradeDescription: this.form.upgradeDescription,// fileId: res.fileId,// fileType: res.appendixName.substring(res.appendixName.lastIndexOf(".") + 1, res.appendixName.length),fileTime: new Date(),createBy: res.createBy,fileSize: res.fileSize.toFixed(2),}addFactoryAppManage(obj).then(response => {this.msgSuccess("新增成功");this.open = false;this.getList();});})}}});},/** 删除按钮操作 */handleDelete(row) {const ids = row.id || this.ids;this.$confirm('是否确认删除?', "警告", {confirmButtonText: "确定",cancelButtonText: "取消",type: "warning"}).then(function() {return delFactoryAppManage(ids);}).then(() => {this.getList();this.msgSuccess("删除成功");}).catch(() => {});},/** 导出按钮操作 */handleExport() {const queryParams = this.queryParams;this.$confirm('是否确认导出所有app版本管理数据项?', "警告", {confirmButtonText: "确定",cancelButtonText: "取消",type: "warning"}).then(() => {this.exportLoading = true;return exportFactoryAppManage(queryParams);}).then(response => {this.download(response.msg);this.exportLoading = false;}).catch(() => {});}},mounted() {this.$nextTick(function() {this.tableHeight = window.innerHeight - this.$refs.table.$el.offsetTop - 160})}
};</script><style scoped>.form-item{width: 100%;}
</style>

2、文件上传组件

<!--文件上传组件(限制1个)-->
<template><div><el-uploadclass="upload-demo"ref="recordUpload":headers="headers":action="uploadUrl":on-remove="handleRemoveRecord":on-progress="uploadProcess":before-upload="beforeUpload":on-success="handleUpFileSuccess":file-list="recordFileList"><el-button size="small" type="primary" style="width: 100%">点击上传</el-button></el-upload><!--    <div class="el-upload__tip" slot="tip"><template>最多上传一个文件,每个文件最大不能超过20MB!!!</template></div>--><!--    文件上传遮罩--><el-dialog :visible.sync="uploadFlag" :show-close="false"><div class="sysFolderManage-body"></div><el-progress v-if="uploadFlag == true" :percentage="videoUploadPercent"></el-progress></el-dialog></div>
</template><script>
import {getToken} from "@/utils/auth";export default {name: "upRecord",data() {return {uploadUrl: process.env.VUE_APP_BASE_API + "/fileManage/uploadWithManage",headers: {Authorization: "Bearer " + getToken(),},uploadFlag: false,videoUploadPercent: 0,recordFileList: [],recordFileSucc: []}},methods: {beforeUpload(file) {if (this.recordFileSucc.length === 1) {this.msgError("单次最多上传3个文件!")return false}//判断文件大小var limitFileSize = file.size / 1024 / 1024 < 30if (!limitFileSize) {this.msgError("上传文件大小不能超过 30MB!")return limitFileSize}},/**文件上传遮罩 进度条*/uploadProcess(event, file, fileList) {this.uploadFlag = true;this.videoUploadPercent = parseInt(event.percent);},//文件上传处理handleUpFileSuccess(res, file, recordList) {if (res.code != 200) {this.msgError(res.msg);} else {this.uploadFlag = false;this.recordFileSucc = []this.handleFileList(recordList)this.$emit('sendRecordData', this.recordFileSucc);}},//文件删除处理handleRemoveRecord(file, recordList) {this.recordFileSucc = []this.handleFileList(recordList)this.$emit('sendRecordData', this.recordFileSucc);},//数据转换handleFileList(recordList) {recordList.filter(a => {this.recordFileSucc.push({fileId: a.response.appendix.id,fileSize: a.size / 1024 / 1024,appendixName: a.response.appendix.appendixName,appendixPath: a.response.appendix.appendixPath,createBy: a.response.appendix.createBy})})}}
}
</script>


http://www.ppmy.cn/ops/105084.html

相关文章

微信小程序知识点(一)

1.条件判断&#xff1a; wx:if&#xff0c;wx:elif&#xff0c;wx:else 和Hidden的区别 wx:if等是动态实现组件的&#xff0c;符合条件&#xff0c;页面上就新增一个组件&#xff0c;不符合&#xff0c;就会在也页面上加载&#xff0c;而Hidden只是控制页面的组件的显示与否&…

停止在 AWS 中使用 SSH!原因如下!DevSecOps 视角

我们要解决什么问题&#xff1f;欢迎来到雲闪世界。 我见过多少次安全组从 10.0.0.0/8 或更糟的 0.0.0.0/0 开放端口 22&#xff1f;太多次了&#xff01;但为什么&#xff0c;为什么在有更好的替代方案的情况下&#xff0c;我们在 2024 年仍在使用 SSH&#xff1f;作为一名安全…

2024/9/3黑马头条跟学笔记(一)

D1 视频链接 Day1-05-nacos环境搭建_哔哩哔哩_bilibili 内容介绍 搭建微服务开发环境&#xff0c;登录接口包含注册中心和nacos配置中心 服务端用户…微服务。网关负载均衡转发接口请求 实现微服务间互相通信 接口测试 前后端联调 前置知识 背景介绍 类似今日头条&#x…

对比 PDAF、CDAF 和 LAAF 自动对焦技术

深入解析相位检测自动对焦&#xff08;PDAF&#xff09; 相位检测自动对焦&#xff08;PDAF&#xff0c;Phase Detection Auto Focus&#xff09;是一种高效的自动对焦技术&#xff0c;广泛应用于现代数码相机、无反相机和智能手机摄像头中。为了更好地理解 PDAF&#xff0c;我…

设计模式学习-命令模式

概念 命令&#xff0c;接收者&#xff0c;执行者&#xff0c;一个命令模式由这些基本的组件组成。 接收者 会有一个函数 命令有一个持有接收者并且 有一个 执行函数 执行者 持有一个命令 并且 会执行这个命令 using UnityEngine; using System.Collections; namespace CommondS…

PHP一键创建全球参与探索现代在线投票系统

一键创建全球参与探索现代在线投票系统 &#x1f310;✨ &#x1f680; 开篇&#xff1a;解锁全球互动新纪元 在这个数字化飞速发展的时代&#xff0c;每一个声音都值得被听见&#xff0c;每一份意见都能跨越山海相连。想象一下&#xff0c;只需轻轻一点&#xff0c;就能发起…

sqlite3的db.interrupt方法深入解析

在Node.js环境中&#xff0c;sqlite3库是一个广受欢迎的轻量级数据库库&#xff0c;它为开发者提供了一个简洁的API来与SQLite数据库进行交互。在处理长时间运行或复杂的数据库查询时&#xff0c;有时可能需要中断这些查询。sqlite3库提供了db.interrupt方法来实现这一功能。本…

集合及映射

1、集合类图 1&#xff09;ArrayList与LinkedList 区别 LinkedList 实现了双向队列的接口&#xff0c;对于数据的插入速度较快&#xff0c;只需要修改前后的指向即可&#xff1b;ArrayList对于特定位置插入数据&#xff0c;需要移动特定位置后面的数据&#xff0c;有额外开销 …