提交 50f29633 编写于 作者: wonain's avatar wonain

增加Excel导入导出示例功能

上级 25f5809a
......@@ -6,6 +6,7 @@ import (
"gin-vue-admin/model/request"
"gin-vue-admin/model/response"
"gin-vue-admin/service"
"gin-vue-admin/utils"
"github.com/gin-gonic/gin"
"go.uber.org/zap"
)
......@@ -78,3 +79,86 @@ func GetFileList(c *gin.Context) {
},"获取成功", c)
}
}
// @Tags ExaFileUploadAndDownload
// @Summary 导出Excel
// @Security ApiKeyAuth
// @accept application/json
// @Produce application/octet-stream
// @Param data body request.ExcelInfo true "导出Excel文件信息"
// @Success 200
// @Router /fileUploadAndDownload/exportExcel [post]
func ExportExcel(c *gin.Context) {
var excelInfo request.ExcelInfo
c.ShouldBindJSON(&excelInfo)
filePath := global.GVA_CONFIG.Excel.Dir+excelInfo.FileName
err := service.ParseInfoList2Excel(excelInfo.InfoList, filePath)
if err != nil {
global.GVA_LOG.Error("转换Excel失败!", zap.Any("err", err))
response.FailWithMessage("转换Excel失败", c)
return
}
c.Writer.Header().Add("success", "true")
c.File(filePath)
}
// @Tags ExaFileUploadAndDownload
// @Summary 导入Excel文件
// @Security ApiKeyAuth
// @accept multipart/form-data
// @Produce application/json
// @Param file formData file true "导入Excel文件"
// @Success 200 {string} string "{"success":true,"data":{},"msg":"导入成功"}"
// @Router /fileUploadAndDownload/importExcel [post]
func ImportExcel(c *gin.Context) {
_, header, err := c.Request.FormFile("file")
if err != nil {
global.GVA_LOG.Error("接收文件失败!", zap.Any("err", err))
response.FailWithMessage("接收文件失败", c)
return
}
c.SaveUploadedFile(header, global.GVA_CONFIG.Excel.Dir+"ExcelImport.xlsx")
response.OkWithMessage("导入成功", c)
}
// @Tags ExaFileUploadAndDownload
// @Summary 加载Excel数据
// @Security ApiKeyAuth
// @Produce application/json
// @Success 200 {string} string "{"success":true,"data":{},"msg":"加载数据成功"}"
// @Router /fileUploadAndDownload/loadExcel [get]
func LoadExcel(c *gin.Context) {
menus, err := service.ParseExcel2InfoList()
if err != nil {
global.GVA_LOG.Error("加载数据失败", zap.Any("err", err))
response.FailWithMessage("加载数据失败", c)
return
}
response.OkWithDetailed(response.PageResult{
List: menus,
Total: int64(len(menus)),
Page: 1,
PageSize: 999,
},"加载数据成功", c)
}
// @Tags ExaFileUploadAndDownload
// @Summary 下载模板
// @Security ApiKeyAuth
// @accept multipart/form-data
// @Produce application/json
// @Param fileName query fileName true "模板名称"
// @Success 200
// @Router /fileUploadAndDownload/downloadTemplate [get]
func DownloadTemplate(c *gin.Context) {
fileName := c.Query("fileName")
filePath := global.GVA_CONFIG.Excel.Dir+fileName
ok, err := utils.PathExists(filePath)
if !ok || err != nil {
global.GVA_LOG.Error("文件不存在", zap.Any("err", err))
response.FailWithMessage("文件不存在", c)
return
}
c.Writer.Header().Add("success", "true")
c.File(filePath)
}
\ No newline at end of file
......@@ -76,4 +76,8 @@ qiniu:
use-https: false
access-key: '25j8dYBZ2wuiy0yhwShytjZDTX662b8xiFguwxzZ'
secret-key: 'pgdbqEsf7ooZh7W3xokP833h3dZ_VecFXPDeG5JY'
use-cdn-domains: false
\ No newline at end of file
use-cdn-domains: false
# excel configuration
excel:
dir: './resource/excel/'
\ No newline at end of file
......@@ -13,4 +13,5 @@ type Server struct {
// oss
Local Local `mapstructure:"local" json:"local" yaml:"local"`
Qiniu Qiniu `mapstructure:"qiniu" json:"qiniu" yaml:"qiniu"`
Excel Excel `mapstructure:"excel" json:"excel" yaml:"excel"`
}
package config
type Excel struct {
Dir string `mapstructure:"dir" json:"dir" yaml:"dir"`
}
\ No newline at end of file
......@@ -3,6 +3,7 @@ module gin-vue-admin
go 1.14
require (
github.com/360EntSecGroup-Skylar/excelize/v2 v2.3.2
github.com/StackExchange/wmi v0.0.0-20190523213315-cbe66965904d // indirect
github.com/alecthomas/template v0.0.0-20190718012654-fb15b899a751
github.com/casbin/casbin v1.9.1
......@@ -47,8 +48,7 @@ require (
github.com/tebeka/strftime v0.1.3 // indirect
github.com/unrolled/secure v1.0.7
go.uber.org/zap v1.10.0
golang.org/x/net v0.0.0-20200324143707-d3edc9973b7e // indirect
golang.org/x/sys v0.0.0-20200610111108-226ff32320da // indirect
golang.org/x/net v0.0.0-20201224014010-6772e930b67b // indirect
golang.org/x/tools v0.0.0-20200324003944-a576cf524670 // indirect
google.golang.org/protobuf v1.24.0 // indirect
gopkg.in/ini.v1 v1.55.0 // indirect
......
package request
import "gin-vue-admin/model"
type ExcelInfo struct {
FileName string `json:"fileName"`
InfoList []model.SysBaseMenu `json:"infoList"`
}
\ No newline at end of file
......@@ -15,5 +15,9 @@ func InitFileUploadAndDownloadRouter(Router *gin.RouterGroup) {
FileUploadAndDownloadGroup.GET("/findFile", v1.FindFile) // 查询当前文件成功的切片
FileUploadAndDownloadGroup.POST("/breakpointContinueFinish", v1.BreakpointContinueFinish) // 查询当前文件成功的切片
FileUploadAndDownloadGroup.POST("/removeChunk", v1.RemoveChunk) // 查询当前文件成功的切片
FileUploadAndDownloadGroup.POST("/importExcel", v1.ImportExcel) // 导入Excel
FileUploadAndDownloadGroup.GET("/loadExcel", v1.LoadExcel) // 加载Excel数据
FileUploadAndDownloadGroup.POST("/exportExcel", v1.ExportExcel) // 导出Excel
FileUploadAndDownloadGroup.GET("/downloadTemplate", v1.DownloadTemplate) // 下载模板文件
}
}
package service
import (
"errors"
"fmt"
"gin-vue-admin/global"
"gin-vue-admin/model"
"github.com/360EntSecGroup-Skylar/excelize/v2"
"strconv"
)
func ParseInfoList2Excel(infoList []model.SysBaseMenu, filePath string) error {
excel := excelize.NewFile()
excel.SetSheetRow("Sheet1","A1",&[]string{"ID","路由Name","路由Path","是否隐藏","父节点","排序","文件名称"})
for i, menu := range infoList {
axis := fmt.Sprintf("A%d",i+2)
excel.SetSheetRow("Sheet1",axis,&[]interface{}{
menu.ID,
menu.Name,
menu.Path,
menu.Hidden,
menu.ParentId,
menu.Sort,
menu.Component,
})
}
excel.SaveAs(filePath)
return nil
}
func ParseExcel2InfoList() ([]model.SysBaseMenu, error) {
skipHeader := true
fixedHeader := []string{"ID","路由Name","路由Path","是否隐藏","父节点","排序","文件名称"}
file, err := excelize.OpenFile(global.GVA_CONFIG.Excel.Dir+"ExcelImport.xlsx")
if err != nil {
return nil, err
}
menus := make([]model.SysBaseMenu, 0)
rows, err := file.Rows("Sheet1")
if err != nil {
return nil, err
}
for rows.Next() {
row, err := rows.Columns()
if err != nil {
return nil, err
}
if skipHeader {
if compareStrSlice(row, fixedHeader) {
skipHeader = false
continue
} else {
return nil, errors.New("Excel格式错误")
}
}
if len(row) != len(fixedHeader) {
continue
}
id, _ := strconv.Atoi(row[0])
hidden, _ := strconv.ParseBool(row[3])
sort, _ := strconv.Atoi(row[5])
menu := model.SysBaseMenu{
GVA_MODEL: global.GVA_MODEL{
ID: uint(id),
},
Name: row[1],
Path: row[2],
Hidden: hidden,
ParentId: row[4],
Sort: sort,
Component: row[6],
}
menus = append(menus, menu)
}
return menus, nil
}
func compareStrSlice(a, b []string) bool {
if len(a) != len(b) {
return false
}
if (b == nil) != (a == nil) {
return false
}
for key, value := range a {
if value != b[key] {
return false
}
}
return true
}
\ No newline at end of file
{
"name": "qm-plus-vue-page",
"name": "gin-vue-admin",
"version": "0.1.0",
"lockfileVersion": 1,
"requires": true,
......@@ -3449,6 +3449,13 @@
"integrity": "sha1-6Bj9ac5cz8tARZT4QpY79TFkzDc=",
"dev": true
},
"emojis-list": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz",
"integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==",
"dev": true,
"optional": true
},
"fast-deep-equal": {
"version": "3.1.3",
"resolved": "https://registry.npm.taobao.org/fast-deep-equal/download/fast-deep-equal-3.1.3.tgz?cache=0&sync_timestamp=1591599659970&other_urls=https%3A%2F%2Fregistry.npm.taobao.org%2Ffast-deep-equal%2Fdownload%2Ffast-deep-equal-3.1.3.tgz",
......@@ -3476,12 +3483,31 @@
"path-exists": "^4.0.0"
}
},
"has-flag": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
"integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
"dev": true,
"optional": true
},
"is-fullwidth-code-point": {
"version": "3.0.0",
"resolved": "https://registry.npm.taobao.org/is-fullwidth-code-point/download/is-fullwidth-code-point-3.0.0.tgz",
"integrity": "sha1-8Rb4Bk/pCz94RKOJl8C3UFEmnx0=",
"dev": true
},
"loader-utils": {
"version": "2.0.0",
"resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.0.tgz",
"integrity": "sha512-rP4F0h2RaWSvPEkD7BLDFQnvSf+nK+wr3ESUjNTyAGobqrijmW92zc+SO6d4p4B1wh7+B/Jg1mkQe5NYUEHtHQ==",
"dev": true,
"optional": true,
"requires": {
"big.js": "^5.2.2",
"emojis-list": "^3.0.0",
"json5": "^2.1.2"
}
},
"locate-path": {
"version": "5.0.0",
"resolved": "https://registry.npm.taobao.org/locate-path/download/locate-path-5.0.0.tgz",
......@@ -3647,6 +3673,16 @@
"ansi-regex": "^5.0.0"
}
},
"supports-color": {
"version": "7.2.0",
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
"integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==",
"dev": true,
"optional": true,
"requires": {
"has-flag": "^4.0.0"
}
},
"terser": {
"version": "4.8.0",
"resolved": "https://registry.npm.taobao.org/terser/download/terser-4.8.0.tgz?cache=0&sync_timestamp=1599751633316&other_urls=https%3A%2F%2Fregistry.npm.taobao.org%2Fterser%2Fdownload%2Fterser-4.8.0.tgz",
......@@ -3685,6 +3721,31 @@
"punycode": "^2.1.1"
}
},
"vue-loader-v16": {
"version": "npm:vue-loader@16.1.2",
"resolved": "https://registry.npmjs.org/vue-loader/-/vue-loader-16.1.2.tgz",
"integrity": "sha512-8QTxh+Fd+HB6fiL52iEVLKqE9N1JSlMXLR92Ijm6g8PZrwIxckgpqjPDWRP5TWxdiPaHR+alUWsnu1ShQOwt+Q==",
"dev": true,
"optional": true,
"requires": {
"chalk": "^4.1.0",
"hash-sum": "^2.0.0",
"loader-utils": "^2.0.0"
},
"dependencies": {
"chalk": {
"version": "4.1.0",
"resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.0.tgz",
"integrity": "sha512-qwx12AxXe2Q5xQ43Ac//I6v5aXTipYrSESdOgzrN+9XjgEpyjpKuvSGaN4qE93f7TQTlerQQ8S+EQ0EyDoVL1A==",
"dev": true,
"optional": true,
"requires": {
"ansi-styles": "^4.1.0",
"supports-color": "^7.1.0"
}
}
}
},
"wrap-ansi": {
"version": "6.2.0",
"resolved": "https://registry.npm.taobao.org/wrap-ansi/download/wrap-ansi-6.2.0.tgz",
......@@ -14937,94 +14998,6 @@
}
}
},
"vue-loader-v16": {
"version": "npm:vue-loader@16.1.1",
"resolved": "https://registry.npmjs.org/vue-loader/-/vue-loader-16.1.1.tgz",
"integrity": "sha512-wz/+HFg/3SBayHWAlZXARcnDTl3VOChrfW9YnxvAweiuyKX/7IGx1ad/4yJHmwhgWlOVYMAbTiI7GV8G33PfGQ==",
"dev": true,
"optional": true,
"requires": {
"chalk": "^4.1.0",
"hash-sum": "^2.0.0",
"loader-utils": "^2.0.0"
},
"dependencies": {
"ansi-styles": {
"version": "4.3.0",
"resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz",
"integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==",
"dev": true,
"optional": true,
"requires": {
"color-convert": "^2.0.1"
}
},
"chalk": {
"version": "4.1.0",
"resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.0.tgz",
"integrity": "sha512-qwx12AxXe2Q5xQ43Ac//I6v5aXTipYrSESdOgzrN+9XjgEpyjpKuvSGaN4qE93f7TQTlerQQ8S+EQ0EyDoVL1A==",
"dev": true,
"optional": true,
"requires": {
"ansi-styles": "^4.1.0",
"supports-color": "^7.1.0"
}
},
"color-convert": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz",
"integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==",
"dev": true,
"optional": true,
"requires": {
"color-name": "~1.1.4"
}
},
"color-name": {
"version": "1.1.4",
"resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz",
"integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==",
"dev": true,
"optional": true
},
"emojis-list": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz",
"integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==",
"dev": true,
"optional": true
},
"has-flag": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
"integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
"dev": true,
"optional": true
},
"loader-utils": {
"version": "2.0.0",
"resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.0.tgz",
"integrity": "sha512-rP4F0h2RaWSvPEkD7BLDFQnvSf+nK+wr3ESUjNTyAGobqrijmW92zc+SO6d4p4B1wh7+B/Jg1mkQe5NYUEHtHQ==",
"dev": true,
"optional": true,
"requires": {
"big.js": "^5.2.2",
"emojis-list": "^3.0.0",
"json5": "^2.1.2"
}
},
"supports-color": {
"version": "7.2.0",
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
"integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==",
"dev": true,
"optional": true,
"requires": {
"has-flag": "^4.0.0"
}
}
}
},
"vue-particle-line": {
"version": "0.1.4",
"resolved": "https://registry.npmjs.org/vue-particle-line/-/vue-particle-line-0.1.4.tgz",
......
......@@ -72,4 +72,4 @@
"> 1%",
"last 2 versions"
]
}
\ No newline at end of file
}
import service from '@/utils/request'
import service from '@/utils/request';
import { Message } from 'element-ui';
const handleFileError = (res, fileName) => {
if (typeof(res.data) !== "undefined") {
if (res.data.type == "application/json") {
const reader = new FileReader();
reader.onload = function() {
let message = JSON.parse(reader.result).msg;
Message({
showClose: true,
message: message,
type: 'error'
})
};
reader.readAsText(new Blob([res.data]));
}
} else {
var downloadUrl = window.URL.createObjectURL(new Blob([res]));
var a = document.createElement('a');
a.style.display = 'none';
a.href = downloadUrl;
a.download = fileName;
var event = new MouseEvent("click");
a.dispatchEvent(event);
}
}
// @Tags FileUploadAndDownload
// @Summary 分页文件列表
// @Security ApiKeyAuth
......@@ -28,4 +55,62 @@ export const deleteFile = (data) => {
method: "post",
data
})
}
// @Tags ExaFileUploadAndDownload
// @Summary 导出Excel
// @Security ApiKeyAuth
// @accept application/json
// @Produce application/octet-stream
// @Param data body request.ExcelInfo true "导出Excel文件信息"
// @Success 200
// @Router /fileUploadAndDownload/exportExcel [post]
export const exportExcel = (tableData, fileName) => {
service({
url: "/fileUploadAndDownload/exportExcel",
method: 'post',
data: {
fileName: fileName,
infoList: tableData
},
responseType: 'blob'
}).then((res)=>{
handleFileError(res, fileName)
})
}
// @Tags ExaFileUploadAndDownload
// @Summary 导入Excel文件
// @Security ApiKeyAuth
// @accept multipart/form-data
// @Produce application/json
// @Param file formData file true "导入Excel文件"
// @Success 200 {string} string "{"success":true,"data":{},"msg":"导入成功"}"
// @Router /fileUploadAndDownload/importExcel [post]
export const loadExcelData = () => {
return service({
url: "/fileUploadAndDownload/loadExcel",
method: 'get'
})
}
// @Tags ExaFileUploadAndDownload
// @Summary 下载模板
// @Security ApiKeyAuth
// @accept multipart/form-data
// @Produce application/json
// @Param fileName query fileName true "模板名称"
// @Success 200
// @Router /fileUploadAndDownload/downloadTemplate [get]
export const downloadTemplate = (fileName) => {
return service({
url: "/fileUploadAndDownload/downloadTemplate",
method: 'get',
params:{
fileName: fileName
},
responseType: 'blob'
}).then((res)=>{
handleFileError(res, fileName)
})
}
\ No newline at end of file
<template>
<div>
<el-upload
:action="`${path}/fileUploadAndDownload/upload`"
:before-remove="beforeRemove"
:file-list="fileList"
:headers="{'x-token':token}"
:limit="10"
:on-exceed="handleExceed"
:on-preview="handlePreview"
:on-remove="handleRemove"
class="upload-demo"
multiple
>
<el-button size="small" type="primary">点击上传</el-button>
<div class="el-upload__tip" slot="tip">未对文件格式及大小做校验</div>
</el-upload>
<div class="upload">
<el-row>
<el-col :span="2">
<el-upload
:action="`${path}/fileUploadAndDownload/importExcel`"
:headers="{'x-token':token}"
:on-success="loadExcel"
:show-file-list="false"
>
<el-button size="small" type="primary" icon="el-icon-upload2">导入</el-button>
</el-upload>
</el-col>
<el-col :span="2">
<el-button size="small" type="primary" icon="el-icon-download" @click="handleExcelExport('ExcelExport.xlsx')">导出</el-button>
</el-col>
<el-col :span="2">
<el-button size="small" type="success" icon="el-icon-download" @click="downloadExcelTemplate()">下载模板</el-button>
</el-col>
</el-row>
<el-table :data="tableData" border row-key="ID" stripe>
<el-table-column label="ID" min-width="100" prop="ID"></el-table-column>
<el-table-column label="路由Name" min-width="160" prop="name"></el-table-column>
<el-table-column label="路由Path" min-width="160" prop="path"></el-table-column>
<el-table-column label="是否隐藏" min-width="100" prop="hidden">
<template slot-scope="scope">
<span>{{scope.row.hidden?"隐藏":"显示"}}</span>
</template>
</el-table-column>
<el-table-column label="父节点" min-width="90" prop="parentId"></el-table-column>
<el-table-column label="排序" min-width="70" prop="sort"></el-table-column>
<el-table-column label="文件路径" min-width="360" prop="component"></el-table-column>
</el-table>
</div>
</template>
<script>
import { mapGetters } from 'vuex'
const path = process.env.VUE_APP_BASE_API
const path = process.env.VUE_APP_BASE_API;
import { mapGetters } from 'vuex';
import infoList from "@/mixins/infoList";
import { exportExcel, loadExcelData, downloadTemplate } from "@/api/fileUploadAndDownload";
import { getMenuList } from "@/api/menu";
export default {
name: 'Excel',
mixins: [infoList],
data() {
return {
path: path,
fileList: [
{
name: 'food.jpeg',
url:
'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'
},
{
name: 'food2.jpeg',
url:
'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'
}
]
listApi: getMenuList,
path: path
}
},
computed: {
...mapGetters('user', ['userInfo', 'token'])
},
methods: {
handleRemove(file, fileList) {
this.$message.warning(
`共有 ${fileList.length} 个文件,移除了${file.name}`
)
handleExcelExport(fileName) {
if (!fileName || typeof fileName !== "string") {
fileName = "ExcelExport.xlsx";
}
exportExcel(this.tableData, fileName);
},
handlePreview(file) {
this.$message.warning(`${file.name}选择完成`)
loadExcel() {
this.listApi = loadExcelData;
this.getTableData();
},
handleExceed(files, fileList) {
this.$message.warning(
`当前限制选择 3 个文件,本次选择了 ${
files.length
} 个文件,共选择了 ${files.length + fileList.length} 个文件`
)
},
beforeRemove(file, fileList) {
return this.$confirm(
`共有 ${fileList.length} 个文件,确定移除 ${file.name}?`
)
downloadExcelTemplate() {
downloadTemplate('ExcelTemplate.xlsx')
}
},
created() {
this.pageSize = 999;
this.getTableData();
}
}
</script>
\ No newline at end of file
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册