85 Commits

Author SHA1 Message Date
RuoYi
ca9ebb3eaa 若依 3.8.2 2022-04-01 08:06:22 +08:00
RuoYi
e27ae2260e update registry source 2022-03-30 10:34:54 +08:00
RuoYi
b16e8cb3f6 topNav自定义隐藏侧边栏路由 2022-03-30 10:34:40 +08:00
RuoYi
bb110de97e 修复用户管理部门查询图片显示问题 2022-03-27 22:21:47 +08:00
RuoYi
32ee59f763 优化控制台出现的ElOnlyChild错误 2022-03-27 21:13:43 +08:00
RuoYi
c58003056f 添加新群号:167385320 2022-03-22 16:50:29 +08:00
RuoYi
7d4b0c6c1e update vite.config.js 2022-03-18 15:11:49 +08:00
若依
a5c8a36031 Merge pull request #37 from wkclz/master
不配置 VITE_BUILD_COMPRESS 情况下,不自动压缩编译产物
2022-03-18 15:03:07 +08:00
RuoYi
59aabc0f81 update vite.config.js 2022-03-18 15:01:07 +08:00
若依
2c952e5af0 Merge pull request #8 from sapuser2017/patch-1
Update vite.config.js
2022-03-18 14:57:09 +08:00
若依
58fc484547 Merge pull request #32 from AcyYu/master
增加支持子路径
2022-03-18 14:52:35 +08:00
wangkc
639f4656f2 不配置 VITE_BUILD_COMPRESS 情况下,不自动压缩编译产物 2022-03-17 22:38:53 +08:00
RuoYi
bab9941aac 修复使用TopNav更多菜单样式不同步问题 2022-03-17 18:41:46 +08:00
RuoYi
18004588ed 修复菜单主类目不能被选择问题 2022-03-17 18:40:55 +08:00
RuoYi
a036b5a124 修复Oracle数据库用户表头像列为null时不显示默认头像问题 2022-03-17 09:45:38 +08:00
RuoYi
a5153cea4c 优化固定Header后顶部导航栏样式问题(I4XDN5) 2022-03-17 09:43:19 +08:00
RuoYi
72f35742d4 优化菜单名称过长悬停显示标题 2022-03-15 14:02:54 +08:00
RuoYi
93caadaadb 开启TopNav没有子菜单情况隐藏侧边栏 2022-03-06 09:00:47 +08:00
acy
963b1da86e 增加支持子路径 2022-03-02 17:15:45 +08:00
RuoYi
6de1250639 服务监控新增运行参数信息显示 2022-02-26 09:51:20 +08:00
RuoYi
8dc3321907 组件fileUpload支持多文件同时选择上传 2022-02-25 11:50:03 +08:00
RuoYi
a7243a17da 组件ImageUpload支持多图同时选择上传 2022-02-25 09:11:15 +08:00
RuoYi
1d42696834 优化部门管理页面email字段的表单验证多余的单引号 2022-02-23 20:48:37 +08:00
RuoYi
becd079766 页面若未匹配到字典标签则返回原字典值 2022-02-23 16:56:35 +08:00
RuoYi
aa564c477e 优化个人中心页面email字段的表单验证多余的单引号 2022-02-23 16:54:47 +08:00
RuoYi
0587b81abd 修复分页组件请求两次问题 2022-02-21 15:19:26 +08:00
RuoYi
8c94c48ab5 修改登录超时刷新页面跳转登录页面还提示重新登录问题 2022-02-19 17:18:19 +08:00
RuoYi
e519e3ef4b 修复表格内预览图片被覆盖问题 2022-02-19 15:30:36 +08:00
RuoYi
9f9a06ab93 修复分页组件请求两次问题 2022-02-19 14:23:31 +08:00
RuoYi
3d24e0ae01 菜单关闭弹窗图标选择隐藏 2022-02-12 16:35:00 +08:00
RuoYi
1e972d9026 升级element-plus到稳定版本 2022-02-12 15:22:38 +08:00
RuoYi
6d63e64505 代码生成编辑修改后同步列表显示 2022-02-12 11:36:58 +08:00
RuoYi
bd3b20e8ad fix css class name 2022-01-23 10:48:59 +08:00
RuoYi
c9e56c663c update copyright 2022 2022-01-18 11:03:48 +08:00
RuoYi
58d573e89b 修复选项卡点击右键刷新丢失参数问题 2022-01-18 11:03:29 +08:00
若依
9f1030d222 Merge pull request #11 from wenhanhan/master
fix-bug -- 使用TreeSelect组件后,重置按钮无法置空该组件值
2022-01-18 11:01:20 +08:00
wenhan
103b08937a fix-bug -- 使用TreeSelect组件后,重置按钮无法置空该组件值 2022-01-12 10:24:25 +08:00
RuoYi
a7b867ff09 适配 element plus 最新版本 2022-01-11 17:24:45 +08:00
RuoYi
b132d44489 添加新群号:264312783 2022-01-11 09:01:13 +08:00
RuoYi
ef93b31af9 update donate 2022-01-04 20:24:56 +08:00
若依
b200753ec9 Create FUNDING.yml 2022-01-04 19:53:24 +08:00
若依
cf89febafa Merge pull request #10 from sapuser2017/patch-2
druid地址修复
2022-01-04 19:44:36 +08:00
RuoYi
7008429ab6 update README.md 2022-01-04 10:49:47 +08:00
java2sap
8e891e0e30 druid地址修复 2022-01-04 09:34:53 +08:00
RuoYi
6075a9d7c1 前端支持设置是否需要防止数据重复提交 2022-01-02 10:35:56 +08:00
RuoYi
13d9251225 空值不进行回显数据字典 2022-01-02 10:24:19 +08:00
RuoYi
4704e92593 update run-web.bat 2022-01-02 10:23:21 +08:00
RuoYi
40c73f37b5 预览组件支持多图显示 2022-01-01 09:46:31 +08:00
RuoYi
33bcab7ecb 代码生成新增Java类型Boolean 2022-01-01 09:39:57 +08:00
java2sap
ac03526ea5 Update vite.config.js
增加新的组件后,vite打包报错@charset,需要增加配置
2021-12-31 13:33:50 +08:00
RuoYi
1f59cedbb0 修复登录失效后多次请求提示多次弹窗问题 2021-12-31 10:04:22 +08:00
RuoYi
f9d754c886 若依 3.8.1 2021-12-31 00:00:09 +08:00
RuoYi
13a5bf8585 修复显示详情信息出现的报错 2021-12-30 15:55:02 +08:00
RuoYi
fa97ed9e2c 新增文件上传组件 2021-12-30 13:50:57 +08:00
RuoYi
cda383534e 新增图片预览组件 2021-12-30 10:51:17 +08:00
RuoYi
61161cdd69 新增图片上传组件 2021-12-30 10:25:40 +08:00
RuoYi
ec4170a4f1 开启通过ip访问的配置 2021-12-30 09:54:06 +08:00
若依
fece6740a4 Merge pull request #5 from littleshe/patch-1
[fix]logo跳转404问题
2021-12-30 09:46:34 +08:00
RuoYi
bb3f449388 修正单词拼写错误 2021-12-29 15:53:30 +08:00
RuoYi
3d7b36932e 用户管理部门查询选择节点后分页参数初始 2021-12-29 15:50:15 +08:00
RuoYi
03a06c3415 定时任务文字修正 2021-12-28 14:56:35 +08:00
RuoYi
6cf9c3ffb6 新增使用Gzip解压缩静态文件地址 2021-12-20 14:47:53 +08:00
RuoYi
5621ea4a29 修复浏览器刷新后页面切换页签无法加载问题 2021-12-18 21:48:05 +08:00
RuoYi
a2aa467030 升级vite-plugin-compression到最新版本0.3.6 2021-12-18 19:16:24 +08:00
RuoYi
f5f717d0d4 升级dart-sass到版本1.45.0 2021-12-18 19:13:35 +08:00
RuoYi
fc372111ae 升级unplugin-auto-import到最新版本0.5.3 2021-12-18 19:09:27 +08:00
RuoYi
ce3c9ef16d 升级echarts到最新版本5.2.2 2021-12-17 15:09:52 +08:00
RuoYi
f13899808f 升级vue到最新版本3.2.26 2021-12-17 15:02:32 +08:00
RuoYi
475e27f4a6 replace @element-plus/icons with @element-plus/icons-vue 2021-12-17 14:43:30 +08:00
RuoYi
f3b1470a5c 升级element-plus到最新版本1.2.0-beta.6 2021-12-17 14:28:14 +08:00
RuoYi
d366a5046d 修复分页选择条/页数不生效问题 2021-12-17 12:08:17 +08:00
RuoYi
02b0bd0ec6 修复菜单图标缺少的prop属性 2021-12-17 12:05:55 +08:00
RuoYi
463011bb66 删除在线用户多余的代码 2021-12-16 15:14:58 +08:00
RuoYi
e170ac272d 代码生成预览溢出显示滚动条 2021-12-15 14:44:05 +08:00
RuoYi
c246d868a9 修改主题颜色按钮尺寸 2021-12-15 14:43:56 +08:00
RuoYi
b6744f8f99 用户导入提示溢出则显示滚动条 2021-12-15 14:43:02 +08:00
RuoYi
674a483ae7 优化下载解析blob异常提示 2021-12-10 10:07:21 +08:00
RuoYi
0c103e53b9 🎉 RuoYi-Cloud-Vue3(Vue3 Element Plus Vite)版本 2021-12-08 17:10:25 +08:00
RuoYi
6db6cecb17 🎉 RuoYi-Vue3(Vue3 Element Plus Vite)版本 2021-12-07 14:58:29 +08:00
RuoYi
6222fb6614 修正用户分配角色属性错误 2021-12-06 20:33:47 +08:00
RuoYi
03fe9f42d9 修复代码生成模板预览格式问题 2021-12-06 17:11:31 +08:00
urrrich
f8037c23ba [fix]logo跳转404问题 2021-12-06 15:57:21 +08:00
若依
f2cf400c8b 🎉 RuoYi-Vue3(Vue3 Element Plus Vite)版本 2021-12-01 17:43:45 +08:00
若依
25e801e579 Delete src/layout/components/tagsView directory
🎉 RuoYi-Vue3(Vue3 Element Plus Vite)版本
2021-12-01 17:43:19 +08:00
RuoYi
3ddb5e9b38 文件夹目录大写 2021-12-01 17:36:12 +08:00
68 changed files with 1183 additions and 499 deletions

View File

@@ -8,4 +8,4 @@ VITE_APP_ENV = 'production'
VITE_APP_BASE_API = '/prod-api'
# 是否在打包时开启压缩,支持 gzip 和 brotli
VITE_BUILD_COMPRESS = gzip,brotli
VITE_BUILD_COMPRESS = gzip

View File

@@ -8,4 +8,4 @@ VITE_APP_ENV = 'staging'
VITE_APP_BASE_API = '/stage-api'
# 是否在打包时开启压缩,支持 gzip 和 brotli
VITE_BUILD_COMPRESS = gzip,brotli
VITE_BUILD_COMPRESS = gzip

1
.github/FUNDING.yml vendored Normal file
View File

@@ -0,0 +1 @@
custom: http://doc.ruoyi.vip/ruoyi-vue/other/donate.html

View File

@@ -1,3 +1,14 @@
<p align="center">
<img alt="logo" src="https://oscimg.oschina.net/oscnet/up-d3d0a9303e11d522a06cd263f3079027715.png">
</p>
<h1 align="center" style="margin: 30px 0 30px; font-weight: bold;">RuoYi v3.8.1</h1>
<h4 align="center">基于SpringBoot+Vue3前后端分离的Java快速开发框架</h4>
<p align="center">
<a href="https://gitee.com/y_project/RuoYi-Vue/stargazers"><img src="https://gitee.com/y_project/RuoYi-Vue/badge/star.svg?theme=dark"></a>
<a href="https://gitee.com/y_project/RuoYi-Vue"><img src="https://img.shields.io/badge/RuoYi-v3.8.1-brightgreen.svg"></a>
<a href="https://gitee.com/y_project/RuoYi-Vue/blob/master/LICENSE"><img src="https://img.shields.io/github/license/mashape/apistatus.svg"></a>
</p>
## 平台简介
* 本仓库为前端技术栈 [Vue3](https://v3.cn.vuejs.org) + [Element Plus](https://element-plus.org/zh-CN) + [Vite](https://cn.vitejs.dev) 版本。
@@ -16,7 +27,7 @@ git clone https://github.com/yangzongzhuan/RuoYi-Vue3.git
cd RuoYi-Vue3
# 安装依赖
yarn --registry=https://registry.npm.taobao.org
yarn --registry=https://registry.npmmirror.com
# 启动服务
yarn dev
@@ -95,4 +106,4 @@ yarn dev
## 若依前后端分离交流群
QQ群 [![加入QQ群](https://img.shields.io/badge/已满-937441-blue.svg)](https://jq.qq.com/?_wv=1027&k=5bVB1og) [![加入QQ群](https://img.shields.io/badge/已满-887144332-blue.svg)](https://jq.qq.com/?_wv=1027&k=5eiA4DH) [![加入QQ群](https://img.shields.io/badge/已满-180251782-blue.svg)](https://jq.qq.com/?_wv=1027&k=5AxMKlC) [![加入QQ群](https://img.shields.io/badge/已满-104180207-blue.svg)](https://jq.qq.com/?_wv=1027&k=51G72yr) [![加入QQ群](https://img.shields.io/badge/已满-186866453-blue.svg)](https://jq.qq.com/?_wv=1027&k=VvjN2nvu) [![加入QQ群](https://img.shields.io/badge/已满-201396349-blue.svg)](https://jq.qq.com/?_wv=1027&k=5vYAqA05) [![加入QQ群](https://img.shields.io/badge/已满-101456076-blue.svg)](https://jq.qq.com/?_wv=1027&k=kOIINEb5) [![加入QQ群](https://img.shields.io/badge/101539465-blue.svg)](https://jq.qq.com/?_wv=1027&k=UKtX5jhs) 点击按钮入群。
QQ群 [![加入QQ群](https://img.shields.io/badge/已满-937441-blue.svg)](https://jq.qq.com/?_wv=1027&k=5bVB1og) [![加入QQ群](https://img.shields.io/badge/已满-887144332-blue.svg)](https://jq.qq.com/?_wv=1027&k=5eiA4DH) [![加入QQ群](https://img.shields.io/badge/已满-180251782-blue.svg)](https://jq.qq.com/?_wv=1027&k=5AxMKlC) [![加入QQ群](https://img.shields.io/badge/已满-104180207-blue.svg)](https://jq.qq.com/?_wv=1027&k=51G72yr) [![加入QQ群](https://img.shields.io/badge/已满-186866453-blue.svg)](https://jq.qq.com/?_wv=1027&k=VvjN2nvu) [![加入QQ群](https://img.shields.io/badge/已满-201396349-blue.svg)](https://jq.qq.com/?_wv=1027&k=5vYAqA05) [![加入QQ群](https://img.shields.io/badge/已满-101456076-blue.svg)](https://jq.qq.com/?_wv=1027&k=kOIINEb5) [![加入QQ群](https://img.shields.io/badge/已满-101539465-blue.svg)](https://jq.qq.com/?_wv=1027&k=UKtX5jhs) [![加入QQ群](https://img.shields.io/badge/已满-264312783-blue.svg)](https://jq.qq.com/?_wv=1027&k=EI9an8lJ) [![加入QQ群](https://img.shields.io/badge/167385320-blue.svg)](https://jq.qq.com/?_wv=1027&k=SWCtLnMz) 点击按钮入群。

View File

@@ -7,6 +7,6 @@ echo.
cd %~dp0
cd ..
yarn --registry=https://registry.npm.taobao.org
yarn --registry=https://registry.npmmirror.com
pause

View File

@@ -1,6 +1,6 @@
@echo off
echo.
echo [<5B><>Ϣ] ʹ<><CAB9> Vue CLI <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> Web <20><><EFBFBD>̡<EFBFBD>
echo [<5B><>Ϣ] ʹ<><CAB9> Vite <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> Web <20><><EFBFBD>̡<EFBFBD>
echo.
%~d0

View File

@@ -1,6 +1,6 @@
{
"name": "ruoyi",
"version": "3.8.0",
"version": "3.8.2",
"description": "若依管理系统",
"author": "若依",
"license": "MIT",
@@ -15,17 +15,16 @@
"url": "https://gitee.com/y_project/RuoYi-Vue.git"
},
"dependencies": {
"@element-plus/icons": "0.0.11",
"@vueuse/core": "6.4.1",
"@element-plus/icons-vue": "0.2.6",
"axios": "0.24.0",
"echarts": "5.2.1",
"element-plus": "1.2.0-beta.3",
"echarts": "5.2.2",
"element-plus": "2.0.1",
"file-saver": "2.0.5",
"fuse.js": "6.4.6",
"js-cookie": "3.0.1",
"jsencrypt": "3.2.1",
"nprogress": "0.2.0",
"vue": "3.2.22",
"vue": "3.2.26",
"vue-cropper": "1.0.2",
"vue-router": "4.0.12",
"vuex": "4.0.2"
@@ -33,10 +32,10 @@
"devDependencies": {
"@vitejs/plugin-vue": "1.9.4",
"@vue/compiler-sfc": "3.2.22",
"sass": "1.43.4",
"unplugin-auto-import": "0.4.18",
"sass": "1.45.0",
"unplugin-auto-import": "0.5.3",
"vite": "2.6.14",
"vite-plugin-compression": "0.3.5",
"vite-plugin-compression": "0.3.6",
"vite-plugin-svg-icons": "1.0.5",
"vite-plugin-vue-setup-extend": "0.1.0"
}

View File

@@ -1,5 +1,5 @@
import request from '@/utils/request'
import { praseStrEmpty } from "@/utils/ruoyi";
import { parseStrEmpty } from "@/utils/ruoyi";
// 查询用户列表
export function listUser(query) {
@@ -13,7 +13,7 @@ export function listUser(query) {
// 查询用户详细
export function getUser(userId) {
return request({
url: '/system/user/' + praseStrEmpty(userId),
url: '/system/user/' + parseStrEmpty(userId),
method: 'get'
})
}

View File

@@ -37,7 +37,7 @@
.mb10 {
margin-bottom: 10px;
}
.ml0 {
.ml10 {
margin-left: 10px;
}
.mt20 {
@@ -49,7 +49,7 @@
.mb20 {
margin-bottom: 20px;
}
.m20 {
.ml20 {
margin-left: 20px;
}
@@ -64,7 +64,7 @@
margin-top: 6vh !important;
}
.el-dialog__wrapper.scrollbar .el-dialog .el-dialog__body {
.el-dialog.scrollbar .el-dialog__body {
overflow: auto;
overflow-x: hidden;
max-height: 70vh;
@@ -112,6 +112,7 @@
border: 1px solid #e5e6e7;
background: #FFFFFF none;
border-radius:4px;
width: 100%;
}
.pagination-container .el-pagination {
@@ -128,7 +129,7 @@
}
}
.el-table .fixed-width .el-button--mini {
.el-table .fixed-width .el-button--small {
padding-left: 0;
padding-right: 0;
width: inherit;
@@ -138,7 +139,7 @@
.el-table .el-dropdown-link {
cursor: pointer;
color: #409EFF;
margin-left: 5px;
margin-left: 10px;
}
.el-table .el-dropdown, .el-icon-arrow-down {
@@ -175,12 +176,12 @@
}
.el-card__header {
padding: 14px 15px 7px;
padding: 14px 15px 7px !important;
min-height: 40px;
}
.el-card__body {
padding: 15px 20px 20px 20px;
padding: 15px 20px 20px 20px !important;
}
.card-box {

View File

@@ -7,6 +7,10 @@
position: relative;
}
.sidebarHide {
margin-left: 0!important;
}
.sidebar-container {
-webkit-transition: width .28s;
transition: width 0.28s;
@@ -66,7 +70,7 @@
width: 100% !important;
}
.el-menu-item, .el-sub-menu__title {
.el-menu-item, .menu-title {
overflow: hidden !important;
text-overflow: ellipsis !important;
white-space: nowrap !important;

View File

@@ -0,0 +1,198 @@
<template>
<div class="upload-file">
<el-upload
multiple
:action="uploadFileUrl"
:before-upload="handleBeforeUpload"
:file-list="fileList"
:limit="limit"
:on-error="handleUploadError"
:on-exceed="handleExceed"
:on-success="handleUploadSuccess"
:show-file-list="false"
:headers="headers"
class="upload-file-uploader"
ref="upload"
>
<!-- 上传按钮 -->
<el-button type="primary">选取文件</el-button>
<!-- 上传提示 -->
<div class="el-upload__tip" v-if="showTip">
请上传
<template v-if="fileSize"> 大小不超过 <b style="color: #f56c6c">{{ fileSize }}MB</b> </template>
<template v-if="fileType"> 格式为 <b style="color: #f56c6c">{{ fileType.join("/") }}</b> </template>
的文件
</div>
</el-upload>
<!-- 文件列表 -->
<transition-group class="upload-file-list el-upload-list el-upload-list--text" name="el-fade-in-linear" tag="ul">
<li :key="file.uid" class="el-upload-list__item ele-upload-list__item-content" v-for="(file, index) in fileList">
<el-link :href="`${baseUrl}${file.url}`" :underline="false" target="_blank">
<span class="el-icon-document"> {{ getFileName(file.name) }} </span>
</el-link>
<div class="ele-upload-list__item-content-action">
<el-link :underline="false" @click="handleDelete(index)" type="danger">删除</el-link>
</div>
</li>
</transition-group>
</div>
</template>
<script setup>
import { getToken } from "@/utils/auth";
const props = defineProps({
modelValue: [String, Object, Array],
// 数量限制
limit: {
type: Number,
default: 5,
},
// 大小限制(MB)
fileSize: {
type: Number,
default: 5,
},
// 文件类型, 例如['png', 'jpg', 'jpeg']
fileType: {
type: Array,
default: () => ["doc", "xls", "ppt", "txt", "pdf"],
},
// 是否显示提示
isShowTip: {
type: Boolean,
default: true
}
});
const { proxy } = getCurrentInstance();
const emit = defineEmits();
const number = ref(0);
const uploadList = ref([]);
const baseUrl = import.meta.env.VITE_APP_BASE_API;
const uploadFileUrl = ref(import.meta.env.VITE_APP_BASE_API + "/common/upload"); // 上传的图片服务器地址
const headers = ref({ Authorization: "Bearer " + getToken() });
const fileList = ref([]);
const showTip = computed(
() => props.isShowTip && (props.fileType || props.fileSize)
);
watch(() => props.modelValue, val => {
if (val) {
let temp = 1;
// 首先将值转为数组
const list = Array.isArray(val) ? val : props.modelValue.split(',');
// 然后将数组转为对象数组
fileList.value = list.map(item => {
if (typeof item === "string") {
item = { name: item, url: item };
}
item.uid = item.uid || new Date().getTime() + temp++;
return item;
});
} else {
fileList.value = [];
return [];
}
});
// 上传前校检格式和大小
function handleBeforeUpload(file) {
// 校检文件类型
if (props.fileType.length) {
let fileExtension = "";
if (file.name.lastIndexOf(".") > -1) {
fileExtension = file.name.slice(file.name.lastIndexOf(".") + 1);
}
const isTypeOk = props.fileType.some((type) => {
if (file.type.indexOf(type) > -1) return true;
if (fileExtension && fileExtension.indexOf(type) > -1) return true;
return false;
});
if (!isTypeOk) {
proxy.$modal.msgError(`文件格式不正确, 请上传${props.fileType.join("/")}格式文件!`);
return false;
}
}
// 校检文件大小
if (props.fileSize) {
const isLt = file.size / 1024 / 1024 < props.fileSize;
if (!isLt) {
proxy.$modal.msgError(`上传文件大小不能超过 ${props.fileSize} MB!`);
return false;
}
}
proxy.$modal.loading("正在上传文件,请稍候...");
number.value++;
return true;
}
// 文件个数超出
function handleExceed() {
proxy.$modal.msgError(`上传文件数量不能超过 ${props.limit} 个!`);
}
// 上传失败
function handleUploadError(err) {
proxy.$modal.msgError("上传文件失败");
}
// 上传成功回调
function handleUploadSuccess(res, file) {
uploadList.value.push({ name: res.fileName, url: res.fileName });
if (uploadList.value.length === number.value) {
fileList.value = fileList.value.concat(uploadList.value);
uploadList.value = [];
number.value = 0;
emit("update:modelValue", listToString(fileList.value));
proxy.$modal.closeLoading();
}
}
// 删除文件
function handleDelete(index) {
fileList.value.splice(index, 1);
emit("update:modelValue", listToString(fileList.value));
}
// 获取文件名称
function getFileName(name) {
if (name.lastIndexOf("/") > -1) {
return name.slice(name.lastIndexOf("/") + 1);
} else {
return "";
}
}
// 对象转成指定字符串分隔
function listToString(list, separator) {
let strs = "";
separator = separator || ",";
for (let i in list) {
strs += list[i].url + separator;
}
return strs != '' ? strs.substr(0, strs.length - 1) : '';
}
</script>
<style scoped lang="scss">
.upload-file-uploader {
margin-bottom: 5px;
}
.upload-file-list .el-upload-list__item {
border: 1px solid #e4e7ed;
line-height: 2;
margin-bottom: 10px;
position: relative;
}
.upload-file-list .ele-upload-list__item-content {
display: flex;
justify-content: space-between;
align-items: center;
color: inherit;
}
.ele-upload-list__item-content-action .el-link {
margin-right: 10px;
}
</style>

View File

@@ -0,0 +1,86 @@
<template>
<el-image
:src="`${realSrc}`"
fit="cover"
:style="`width:${realWidth};height:${realHeight};`"
:preview-src-list="realSrcList"
append-to-body="true"
>
<template #error>
<div class="image-slot">
<el-icon><picture-filled /></el-icon>
</div>
</template>
</el-image>
</template>
<script setup>
import { isExternal } from "@/utils/validate";
const props = defineProps({
src: {
type: String,
required: true
},
width: {
type: [Number, String],
default: ""
},
height: {
type: [Number, String],
default: ""
}
});
const realSrc = computed(() => {
let real_src = props.src.split(",")[0];
if (isExternal(real_src)) {
return real_src;
}
return import.meta.env.VITE_APP_BASE_API + real_src;
});
const realSrcList = computed(() => {
let real_src_list = props.src.split(",");
let srcList = [];
real_src_list.forEach(item => {
if (isExternal(item)) {
return srcList.push(item);
}
return srcList.push(import.meta.env.VITE_APP_BASE_API + item);
});
return srcList;
});
const realWidth = computed(() =>
typeof props.width == "string" ? props.width : `${props.width}px`
);
const realHeight = computed(() =>
typeof props.height == "string" ? props.height : `${props.height}px`
);
</script>
<style lang="scss" scoped>
.el-image {
border-radius: 5px;
background-color: #ebeef5;
box-shadow: 0 0 5px 1px #ccc;
:deep(.el-image__inner) {
transition: all 0.3s;
cursor: pointer;
&:hover {
transform: scale(1.2);
}
}
:deep(.image-slot) {
display: flex;
justify-content: center;
align-items: center;
width: 100%;
height: 100%;
color: #909399;
font-size: 30px;
}
}
</style>

View File

@@ -0,0 +1,206 @@
<template>
<div class="component-upload-image">
<el-upload
multiple
:action="uploadImgUrl"
list-type="picture-card"
:on-success="handleUploadSuccess"
:before-upload="handleBeforeUpload"
:limit="limit"
:on-error="handleUploadError"
:on-exceed="handleExceed"
name="file"
:on-remove="handleRemove"
:show-file-list="true"
:headers="headers"
:file-list="fileList"
:on-preview="handlePictureCardPreview"
:class="{ hide: fileList.length >= limit }"
>
<el-icon class="avatar-uploader-icon"><plus /></el-icon>
</el-upload>
<!-- 上传提示 -->
<div class="el-upload__tip" v-if="showTip">
请上传
<template v-if="fileSize">
大小不超过 <b style="color: #f56c6c">{{ fileSize }}MB</b>
</template>
<template v-if="fileType">
格式为 <b style="color: #f56c6c">{{ fileType.join("/") }}</b>
</template>
的文件
</div>
<el-dialog
v-model="dialogVisible"
title="预览"
width="800px"
append-to-body
>
<img
:src="dialogImageUrl"
style="display: block; max-width: 100%; margin: 0 auto"
/>
</el-dialog>
</div>
</template>
<script setup>
import { getToken } from "@/utils/auth";
const props = defineProps({
modelValue: [String, Object, Array],
// 图片数量限制
limit: {
type: Number,
default: 5,
},
// 大小限制(MB)
fileSize: {
type: Number,
default: 5,
},
// 文件类型, 例如['png', 'jpg', 'jpeg']
fileType: {
type: Array,
default: () => ["png", "jpg", "jpeg"],
},
// 是否显示提示
isShowTip: {
type: Boolean,
default: true
},
});
const { proxy } = getCurrentInstance();
const emit = defineEmits();
const number = ref(0);
const uploadList = ref([]);
const dialogImageUrl = ref("");
const dialogVisible = ref(false);
const baseUrl = import.meta.env.VITE_APP_BASE_API;
const uploadImgUrl = ref(import.meta.env.VITE_APP_BASE_API + "/common/upload"); // 上传的图片服务器地址
const headers = ref({ Authorization: "Bearer " + getToken() });
const fileList = ref([]);
const showTip = computed(
() => props.isShowTip && (props.fileType || props.fileSize)
);
watch(() => props.modelValue, val => {
if (val) {
// 首先将值转为数组
const list = Array.isArray(val) ? val : props.modelValue.split(",");
// 然后将数组转为对象数组
fileList.value = list.map(item => {
if (typeof item === "string") {
if (item.indexOf(baseUrl) === -1) {
item = { name: baseUrl + item, url: baseUrl + item };
} else {
item = { name: item, url: item };
}
}
return item;
});
} else {
fileList.value = [];
return [];
}
});
// 删除图片
function handleRemove(file, files) {
const findex = fileList.value.map(f => f.name).indexOf(file.name);
if (findex > -1) {
fileList.value.splice(findex, 1);
emit("update:modelValue", listToString(fileList.value));
}
}
// 上传成功回调
function handleUploadSuccess(res) {
uploadList.value.push({ name: res.fileName, url: res.fileName });
if (uploadList.value.length === number.value) {
fileList.value = fileList.value.concat(uploadList.value);
uploadList.value = [];
number.value = 0;
emit("update:modelValue", listToString(fileList.value));
proxy.$modal.closeLoading();
}
}
// 上传前loading加载
function handleBeforeUpload(file) {
let isImg = false;
if (props.fileType.length) {
let fileExtension = "";
if (file.name.lastIndexOf(".") > -1) {
fileExtension = file.name.slice(file.name.lastIndexOf(".") + 1);
}
isImg = props.fileType.some(type => {
if (file.type.indexOf(type) > -1) return true;
if (fileExtension && fileExtension.indexOf(type) > -1) return true;
return false;
});
} else {
isImg = file.type.indexOf("image") > -1;
}
if (!isImg) {
proxy.$modal.msgError(
`文件格式不正确, 请上传${props.fileType.join("/")}图片格式文件!`
);
return false;
}
if (props.fileSize) {
const isLt = file.size / 1024 / 1024 < props.fileSize;
if (!isLt) {
proxy.$modal.msgError(`上传头像图片大小不能超过 ${props.fileSize} MB!`);
return false;
}
}
proxy.$modal.loading("正在上传图片,请稍候...");
number.value++;
}
// 文件个数超出
function handleExceed() {
proxy.$modal.msgError(`上传文件数量不能超过 ${props.limit} 个!`);
}
// 上传失败
function handleUploadError() {
proxy.$modal.msgError("上传图片失败");
proxy.$modal.closeLoading();
}
// 预览
function handlePictureCardPreview(file) {
dialogImageUrl.value = file.url;
dialogVisible.value = true;
}
// 对象转成指定字符串分隔
function listToString(list, separator) {
let strs = "";
separator = separator || ",";
for (let i in list) {
strs += list[i].url.replace(baseUrl, "") + separator;
}
return strs != "" ? strs.substr(0, strs.length - 1) : "";
}
</script>
<style scoped lang="scss">
// .el-upload--picture-card 控制加号部分
:deep(.hide .el-upload--picture-card) {
display: none;
}
// 去掉动画效果
:deep(.el-list-enter-active),
:deep(.el-list-leave-active) {
transition: all 0s;
}
:deep(.el-list-enter, .el-list-leave-active) {
opacity: 0;
transform: translateY(0);
}
</style>

View File

@@ -3,7 +3,7 @@
<el-pagination
:background="background"
v-model:current-page="currentPage"
:page-size="pageSize"
v-model:page-size="pageSize"
:layout="layout"
:page-sizes="pageSizes"
:pager-count="pagerCount"
@@ -77,6 +77,9 @@ const pageSize = computed({
}
})
function handleSizeChange(val) {
if (currentPage.value * val > props.total) {
currentPage.value = 1
}
emit('pagination', { page: currentPage.value, limit: val })
if (props.autoScroll) {
scrollTo(0, 800)

View File

@@ -2,13 +2,13 @@
<div class="top-right-btn">
<el-row>
<el-tooltip class="item" effect="dark" :content="showSearch ? '隐藏搜索' : '显示搜索'" placement="top">
<el-button size="mini" circle icon="Search" @click="toggleSearch()" />
<el-button circle icon="Search" @click="toggleSearch()" />
</el-tooltip>
<el-tooltip class="item" effect="dark" content="刷新" placement="top">
<el-button size="mini" circle icon="Refresh" @click="refresh()" />
<el-button circle icon="Refresh" @click="refresh()" />
</el-tooltip>
<el-tooltip class="item" effect="dark" content="显隐列" placement="top" v-if="columns">
<el-button size="mini" circle icon="Menu" @click="showColumn()" />
<el-button circle icon="Menu" @click="showColumn()" />
</el-tooltip>
</el-row>
<el-dialog :title="title" v-model="open" append-to-body>
@@ -76,7 +76,6 @@ for (let item in props.columns) {
<style lang='scss' scoped>
:deep(.el-transfer__button) {
border-radius: 50%;
padding: 12px;
display: block;
margin-left: 0px;
}

View File

@@ -24,10 +24,9 @@ const route = useRoute();
const router = useRouter();
const {proxy} = getCurrentInstance();
const sizeOptions = ref([
{ label: 'Large', value: 'large' },
{ label: 'Medium', value: 'medium' },
{ label: 'Small', value: 'small' },
{ label: 'Mini', value: 'mini' }
{ label: '较大', value: 'large' },
{ label: '默认', value: 'default' },
{ label: '稍小', value: 'small' },
])
function refreshView() {
@@ -43,13 +42,9 @@ function refreshView() {
})
}
function handleSetSize(size) {
proxy.$ELEMENT.size = size;
proxy.$modal.loading("正在设置布局大小,请稍候...");
store.dispatch('app/setSize', size)
refreshView()
ElMessage({
message: 'Switch Size Success',
type: 'success'
})
setTimeout("window.location.reload()", 1000)
};
</script>

View File

@@ -1,4 +1,5 @@
import * as components from "@element-plus/icons";
import * as components from '@element-plus/icons-vue'
export default {
install: (app) => {
for (const key in components) {

View File

@@ -33,13 +33,14 @@ import { isHttp } from '@/utils/validate'
// 顶部栏初始数
const visibleNumber = ref(null);
// 是否为首次加载
const isFrist = ref(null);
// 当前激活菜单的 index
const currentIndex = ref(null);
// 隐藏侧边栏路由
const hideList = ['/index', '/user/profile'];
const store = useStore();
const route = useRoute();
const router = useRouter();
// 主题颜色
const theme = computed(() => store.state.settings.theme);
@@ -69,7 +70,7 @@ const childrenMenus = computed(() => {
for (let item in router.children) {
if (router.children[item].parentPath === undefined) {
if(router.path === "/") {
router.children[item].path = "/redirect/" + router.children[item].path;
router.children[item].path = "/" + router.children[item].path;
} else {
if(!isHttp(router.children[item].path)) {
router.children[item].path = router.path + "/" + router.children[item].path;
@@ -86,52 +87,41 @@ const childrenMenus = computed(() => {
// 默认激活的菜单
const activeMenu = computed(() => {
const path = route.path;
let activePath = defaultRouter.value;
if (path !== undefined && path.lastIndexOf("/") > 0) {
let activePath = path;
if (path !== undefined && path.lastIndexOf("/") > 0 && hideList.indexOf(path) === -1) {
const tmpPath = path.substring(1, path.length);
activePath = "/" + tmpPath.substring(0, tmpPath.indexOf("/"));
} else if ("/index" == path || "" == path) {
if (!isFrist.value) {
isFrist.value = true;
} else {
activePath = "index";
}
}
let routes = activeRoutes(activePath);
if (routes.length === 0) {
activePath = currentIndex.value || defaultRouter.value
activeRoutes(activePath);
store.dispatch('app/toggleSideBarHide', false);
} else if(!route.children) {
activePath = path;
store.dispatch('app/toggleSideBarHide', true);
}
activeRoutes(activePath);
return activePath;
})
// 默认激活的路由
const defaultRouter = computed(() => {
let router;
Object.keys(routers.value).some((key) => {
if (!routers.value[key].hidden) {
router = routers.value[key].path;
return true;
}
});
return router;
})
function setVisibleNumber() {
const width = document.body.getBoundingClientRect().width / 3;
visibleNumber.value = parseInt(width / 85);
}
function handleSelect(key, keyPath) {
currentIndex.value = key;
const route = routers.value.find(item => item.path === key);
if (isHttp(key)) {
// http(s):// 路径新窗口打开
window.open(key, "_blank");
} else if (key.indexOf("/redirect") !== -1) {
// /redirect 路径内部打开
router.push({ path: key.replace("/redirect", "") });
} else if (!route || !route.children) {
// 没有子路由路径内部打开
router.push({ path: key });
store.dispatch('app/toggleSideBarHide', true);
} else {
// 显示左侧联动菜单
activeRoutes(key);
store.dispatch('app/toggleSideBarHide', false);
}
}
function activeRoutes(key) {
let routes = [];
if (childrenMenus.value && childrenMenus.value.length > 0) {
@@ -175,7 +165,7 @@ onMounted(() => {
}
/* sub-menu item */
.topmenu-container.el-menu--horizontal > .el-sub-menu .el-submenu__title {
.topmenu-container.el-menu--horizontal > .el-sub-menu .el-sub-menu__title {
float: left;
height: 50px !important;
line-height: 50px !important;

View File

@@ -82,13 +82,15 @@ const defaultExpandedKey = ref([]);
function initHandle() {
nextTick(() => {
const selectedValue = valueId.value;
if(selectedValue !== null && typeof (selectedValue) !== "undefined"){
if(selectedValue !== null && typeof (selectedValue) !== 'undefined') {
const node = proxy.$refs.selectTree.getNode(selectedValue)
if (node) {
valueTitle.value = node.data[props.objMap.label]
proxy.$refs.selectTree.setCurrentKey(selectedValue) // 设置默认选中
defaultExpandedKey.value = [selectedValue] // 设置默认展开
}
} else {
clearHandle()
}
})
}
@@ -138,7 +140,7 @@ watch(valueId, () => {
font-weight: normal;
}
ul li .el-tree .el-tree-node__content {
ul li .el-tree .el-tree-node__content {
height: auto;
padding: 0 20px;
box-sizing: border-box;

View File

@@ -12,6 +12,8 @@
<script setup>
let store = useStore()
const route = useRoute()
store.dispatch('tagsView/addCachedView', route)
const cachedViews = computed(() => {
return store.state.tagsView.cachedViews
})

View File

@@ -23,7 +23,7 @@
</el-tooltip>
</template>
<div class="avatar-container">
<el-dropdown class="right-menu-item hover-effect" trigger="click">
<el-dropdown @command="handleCommand" class="right-menu-item hover-effect" trigger="click">
<div class="avatar-wrapper">
<img :src="getters.avatar" class="user-avatar" />
<el-icon><caret-bottom /></el-icon>
@@ -33,10 +33,10 @@
<router-link to="/user/profile">
<el-dropdown-item>个人中心</el-dropdown-item>
</router-link>
<el-dropdown-item @click="setLayout">
<el-dropdown-item command="setLayout">
<span>布局设置</span>
</el-dropdown-item>
<el-dropdown-item divided @click="logout">
<el-dropdown-item divided command="logout">
<span>退出登录</span>
</el-dropdown-item>
</el-dropdown-menu>
@@ -65,6 +65,19 @@ function toggleSideBar() {
store.dispatch('app/toggleSideBar')
}
function handleCommand(command) {
switch (command) {
case "setLayout":
setLayout();
break;
case "logout":
logout();
break;
default:
break;
}
}
function logout() {
ElMessageBox.confirm('确定注销并退出系统吗?', '提示', {
confirmButtonText: '确定',

View File

@@ -72,8 +72,8 @@
<el-divider />
<el-button size="small" type="primary" plain icon="DocumentAdd" @click="saveSetting">保存配置</el-button>
<el-button size="small" plain icon="Refresh" @click="resetSetting">重置配置</el-button>
<el-button type="primary" plain icon="DocumentAdd" @click="saveSetting">保存配置</el-button>
<el-button plain icon="Refresh" @click="resetSetting">重置配置</el-button>
</el-drawer>
</template>
@@ -102,6 +102,7 @@ const topNav = computed({
value: val
})
if (!val) {
store.dispatch('app/toggleSideBarHide', false);
store.commit("SET_SIDEBAR_ROUTERS", store.state.permission.defaultRoutes);
}
}

View File

@@ -4,7 +4,7 @@
<app-link v-if="onlyOneChild.meta" :to="resolvePath(onlyOneChild.path, onlyOneChild.query)">
<el-menu-item :index="resolvePath(onlyOneChild.path)" :class="{ 'submenu-title-noDropdown': !isNest }">
<svg-icon :icon-class="onlyOneChild.meta.icon || (item.meta && item.meta.icon)"/>
<template #title>{{ onlyOneChild.meta.title }}</template>
<template #title><span class="menu-title" :title="hasTitle(onlyOneChild.meta.title)">{{ onlyOneChild.meta.title }}</span></template>
</el-menu-item>
</app-link>
</template>
@@ -12,7 +12,7 @@
<el-sub-menu v-else ref="subMenu" :index="resolvePath(item.path)" popper-append-to-body>
<template v-if="item.meta" #title>
<svg-icon :icon-class="item.meta && item.meta.icon" />
<span>{{ item.meta.title }}</span>
<span class="menu-title" :title="hasTitle(item.meta.title)">{{ item.meta.title }}</span>
</template>
<sidebar-item
@@ -91,4 +91,12 @@ function resolvePath(routePath, routeQuery) {
}
return getNormalPath(props.basePath + '/' + routePath)
}
function hasTitle(title){
if (title.length > 5) {
return title;
} else {
return "";
}
}
</script>

View File

@@ -13,7 +13,7 @@
const tagAndTagSpacing = ref(4);
const { proxy } = getCurrentInstance();
const scrollWrapper = computed(() => proxy.$refs.scrollContainer.$refs.wrap);
const scrollWrapper = computed(() => proxy.$refs.scrollContainer.$refs.wrap$);
onMounted(() => {
scrollWrapper.value.addEventListener('scroll', emitScroll, true)

View File

@@ -1,8 +1,8 @@
<template>
<div :class="classObj" class="app-wrapper" :style="{ '--current-color': theme }">
<div v-if="device === 'mobile' && sidebar.opened" class="drawer-bg" @click="handleClickOutside"/>
<sidebar class="sidebar-container" />
<div :class="{ hasTagsView: needTagsView }" class="main-container">
<sidebar v-if="!sidebar.hide" class="sidebar-container" />
<div :class="{ hasTagsView: needTagsView, sidebarHide: sidebar.hide }" class="main-container">
<div :class="{ 'fixed-header': fixedHeader }">
<navbar @setLayout="setLayout" />
<tags-view v-if="needTagsView" />
@@ -98,6 +98,10 @@ function setLayout() {
width: calc(100% - 54px);
}
.sidebarHide .fixed-header {
width: 100%;
}
.mobile .fixed-header {
width: 100%;
}

View File

@@ -31,6 +31,12 @@ import { parseTime, resetForm, addDateRange, handleTree, selectDictLabel } from
import Pagination from '@/components/Pagination'
// 自定义表格工具组件
import RightToolbar from '@/components/RightToolbar'
// 文件上传组件
import FileUpload from "@/components/FileUpload"
// 图片上传组件
import ImageUpload from "@/components/ImageUpload"
// 图片预览组件
import ImagePreview from "@/components/ImagePreview"
// 自定义树选择组件
import TreeSelect from '@/components/TreeSelect'
// 字典标签组件
@@ -51,6 +57,9 @@ app.config.globalProperties.selectDictLabel = selectDictLabel
app.component('DictTag', DictTag)
app.component('Pagination', Pagination)
app.component('TreeSelect', TreeSelect)
app.component('FileUpload', FileUpload)
app.component('ImageUpload', ImageUpload)
app.component('ImagePreview', ImagePreview)
app.component('RightToolbar', RightToolbar)
app.use(router)
@@ -64,7 +73,8 @@ directive(app)
// 使用element-plus 并且设置全局的大小
app.use(ElementPlus, {
locale: locale,
size: Cookies.get('size') || 'medium'
// 支持 large、default、small
size: Cookies.get('size') || 'default'
})
app.mount('#app')

View File

@@ -5,6 +5,7 @@ import NProgress from 'nprogress'
import 'nprogress/nprogress.css'
import { getToken } from '@/utils/auth'
import { isHttp } from '@/utils/validate'
import { isRelogin } from '@/utils/request'
NProgress.configure({ showSpinner: false });
@@ -20,8 +21,10 @@ router.beforeEach((to, from, next) => {
NProgress.done()
} else {
if (store.getters.roles.length === 0) {
isRelogin.show = true
// 判断当前用户是否已拉取完user_info信息
store.dispatch('GetInfo').then(() => {
isRelogin.show = false
store.dispatch('GenerateRoutes').then(accessRoutes => {
// 根据roles权限生成可访问的路由表
accessRoutes.forEach(route => {

View File

@@ -2,6 +2,7 @@ import axios from 'axios'
import { ElMessage } from 'element-plus'
import { saveAs } from 'file-saver'
import { getToken } from '@/utils/auth'
import errorCode from '@/utils/errorCode'
import { blobValidate } from '@/utils/ruoyi'
const baseURL = import.meta.env.VITE_APP_BASE_API
@@ -15,12 +16,12 @@ export default {
responseType: 'blob',
headers: { 'Authorization': 'Bearer ' + getToken() }
}).then(async (res) => {
const isLogin = await this.blobValidate(res.data);
const isLogin = await blobValidate(res.data);
if (isLogin) {
const blob = new Blob([res.data])
this.saveAs(blob, decodeURI(res.headers['download-filename']))
} else {
ElMessage.error('无效的会话,或者会话已过期,请重新登录。');
this.printErrMsg(res.data);
}
})
},
@@ -32,12 +33,12 @@ export default {
responseType: 'blob',
headers: { 'Authorization': 'Bearer ' + getToken() }
}).then(async (res) => {
const isLogin = await this.blobValidate(res.data);
const isLogin = await blobValidate(res.data);
if (isLogin) {
const blob = new Blob([res.data])
this.saveAs(blob, decodeURI(res.headers['download-filename']))
} else {
ElMessage.error('无效的会话,或者会话已过期,请重新登录。');
this.printErrMsg(res.data);
}
})
},
@@ -54,12 +55,18 @@ export default {
const blob = new Blob([res.data], { type: 'application/zip' })
this.saveAs(blob, name)
} else {
ElMessage.error('无效的会话,或者会话已过期,请重新登录。');
this.printErrMsg(res.data);
}
})
},
saveAs(text, name, opts) {
saveAs(text, name, opts);
},
async printErrMsg(data) {
const resText = await data.text();
const rspObj = JSON.parse(resText);
const errMsg = errorCode[rspObj.code] || rspObj.msg || errorCode['default']
ElMessage.error(errMsg);
}
}

View File

@@ -4,20 +4,21 @@ import router from '@/router'
export default {
// 刷新当前tab页签
refreshPage(obj) {
const { path, matched } = router.currentRoute.value;
const { path, query, matched } = router.currentRoute.value;
if (obj === undefined) {
matched.forEach((m) => {
if (m.components && m.components.default && m.components.default.name) {
if (!['Layout', 'ParentView'].includes(m.components.default.name)) {
obj = { name: m.components.default.name, path: path };
obj = { name: m.components.default.name, path: path, query: query };
}
}
});
}
return store.dispatch('tagsView/delCachedView', obj).then(() => {
const { path } = obj
const { path, query } = obj
router.replace({
path: '/redirect' + path
path: '/redirect' + path,
query: query
})
})
},

View File

@@ -57,7 +57,7 @@ export const constantRoutes = [
{
path: '',
component: Layout,
redirect: 'index',
redirect: '/index',
children: [
{
path: '/index',
@@ -139,7 +139,7 @@ export const constantRoutes = [
hidden: true,
children: [
{
path: 'index',
path: 'index/:tableId(\\d+)',
component: () => import('@/views/tool/gen/editTable'),
name: 'GenEdit',
meta: { title: '修改生成配置', activeMenu: '/tool/gen' }
@@ -160,4 +160,4 @@ const router = createRouter({
},
});
export default router;
export default router;

View File

@@ -3,14 +3,18 @@ import Cookies from 'js-cookie'
const state = {
sidebar: {
opened: Cookies.get('sidebarStatus') ? !!+Cookies.get('sidebarStatus') : true,
withoutAnimation: false
withoutAnimation: false,
hide: false
},
device: 'desktop',
size: Cookies.get('size') || 'medium'
size: Cookies.get('size') || 'default'
}
const mutations = {
TOGGLE_SIDEBAR: state => {
if (state.sidebar.hide) {
return false;
}
state.sidebar.opened = !state.sidebar.opened
state.sidebar.withoutAnimation = false
if (state.sidebar.opened) {
@@ -30,6 +34,9 @@ const mutations = {
SET_SIZE: (state, size) => {
state.size = size
Cookies.set('size', size)
},
SET_SIDEBAR_HIDE: (state, status) => {
state.sidebar.hide = status
}
}
@@ -45,6 +52,9 @@ const actions = {
},
setSize({ commit }, size) {
commit('SET_SIZE', size)
},
toggleSideBarHide({ commit }, status) {
commit('SET_SIDEBAR_HIDE', status)
}
}

View File

@@ -24,12 +24,7 @@ const permission = {
state.defaultRoutes = constantRoutes.concat(routes)
},
SET_TOPBAR_ROUTES: (state, routes) => {
// 顶部导航菜单默认添加统计报表栏指向首页
const index = [{
path: 'index',
meta: { title: '统计报表', icon: 'dashboard' }
}]
state.topbarRouters = routes.concat(index);
state.topbarRouters = routes
},
SET_SIDEBAR_ROUTERS: (state, routes) => {
state.sidebarRouters = routes

View File

@@ -52,7 +52,7 @@ const user = {
return new Promise((resolve, reject) => {
getInfo().then(res => {
const user = res.user
const avatar = user.avatar == "" ? defAva : import.meta.env.VITE_APP_BASE_API + user.avatar;
const avatar = (user.avatar == "" || user.avatar == null) ? defAva : import.meta.env.VITE_APP_BASE_API + user.avatar;
if (res.roles && res.roles.length > 0) { // 验证返回的roles是否是一个非空数组
commit('SET_ROLES', res.roles)

View File

@@ -4,9 +4,12 @@ import store from '@/store'
import { getToken } from '@/utils/auth'
import errorCode from '@/utils/errorCode'
import { tansParams, blobValidate } from '@/utils/ruoyi'
import cache from '@/plugins/cache'
import { saveAs } from 'file-saver'
let downloadLoadingInstance;
// 是否显示重新登录
export let isRelogin = { show: false };
axios.defaults.headers['Content-Type'] = 'application/json;charset=utf-8'
// 创建axios实例
@@ -21,6 +24,8 @@ const service = axios.create({
service.interceptors.request.use(config => {
// 是否需要设置 token
const isToken = (config.headers || {}).isToken === false
// 是否需要防止数据重复提交
const isRepeatSubmit = (config.headers || {}).repeatSubmit === false
if (getToken() && !isToken) {
config.headers['Authorization'] = 'Bearer ' + getToken() // 让每个请求携带自定义token 请根据实际情况自行修改
}
@@ -31,6 +36,29 @@ service.interceptors.request.use(config => {
config.params = {};
config.url = url;
}
if (!isRepeatSubmit && (config.method === 'post' || config.method === 'put')) {
const requestObj = {
url: config.url,
data: typeof config.data === 'object' ? JSON.stringify(config.data) : config.data,
time: new Date().getTime()
}
const sessionObj = cache.session.getJSON('sessionObj')
if (sessionObj === undefined || sessionObj === null || sessionObj === '') {
cache.session.setJSON('sessionObj', requestObj)
} else {
const s_url = sessionObj.url; // 请求地址
const s_data = sessionObj.data; // 请求数据
const s_time = sessionObj.time; // 请求时间
const interval = 1000; // 间隔时间(ms),小于此时间视为重复提交
if (s_data === requestObj.data && requestObj.time - s_time < interval && s_url === requestObj.url) {
const message = '数据正在处理,请勿重复提交';
console.warn(`[${s_url}]: ` + message)
return Promise.reject(new Error(message))
} else {
cache.session.setJSON('sessionObj', requestObj)
}
}
}
return config
}, error => {
console.log(error)
@@ -48,16 +76,22 @@ service.interceptors.response.use(res => {
return res.data
}
if (code === 401) {
ElMessageBox.confirm('登录状态已过期,您可以继续留在该页面,或者重新登录', '系统提示', {
if (!isRelogin.show) {
isRelogin.show = true;
ElMessageBox.confirm('登录状态已过期,您可以继续留在该页面,或者重新登录', '系统提示', {
confirmButtonText: '重新登录',
cancelButtonText: '取消',
type: 'warning'
}
).then(() => {
isRelogin.show = false;
store.dispatch('LogOut').then(() => {
location.href = '/index';
})
}).catch(() => {});
}).catch(() => {
isRelogin.show = false;
});
}
return Promise.reject('无效的会话,或者会话已过期,请重新登录。')
} else if (code === 500) {
ElMessage({
@@ -108,12 +142,15 @@ export function download(url, params, filename) {
const blob = new Blob([data])
saveAs(blob, filename)
} else {
ELMessage.error('无效的会话,或者会话已过期,请重新登录。');
const resText = await data.text();
const rspObj = JSON.parse(resText);
const errMsg = errorCode[rspObj.code] || rspObj.msg || errorCode['default']
ElMessage.error(errMsg);
}
downloadLoadingInstance.close();
}).catch((r) => {
console.error(r)
ELMessage.error('下载文件出现错误,请联系管理员!')
ElMessage.error('下载文件出现错误,请联系管理员!')
downloadLoadingInstance.close();
})
}

View File

@@ -70,6 +70,9 @@ export function addDateRange(params, dateRange, propName) {
// 回显数据字典
export function selectDictLabel(datas, value) {
if (value === undefined) {
return "";
}
var actions = [];
Object.keys(datas).some((key) => {
if (datas[key].value == ('' + value)) {
@@ -77,20 +80,31 @@ export function selectDictLabel(datas, value) {
return true;
}
})
if (actions.length === 0) {
actions.push(value);
}
return actions.join('');
}
// 回显数据字典(字符串数组)
export function selectDictLabels(datas, value, separator) {
if (value === undefined) {
return "";
}
var actions = [];
var currentSeparator = undefined === separator ? "," : separator;
var temp = value.split(currentSeparator);
Object.keys(value.split(currentSeparator)).some((val) => {
var match = false;
Object.keys(datas).some((key) => {
if (datas[key].value == ('' + temp[val])) {
actions.push(datas[key].label + currentSeparator);
match = true;
}
})
if (!match) {
actions.push(temp[val] + currentSeparator);
}
})
return actions.join('').substring(0, actions.join('').length - 1);
}
@@ -110,7 +124,7 @@ export function sprintf(str) {
}
// 转换字符串undefined,null等转化为""
export function praseStrEmpty(str) {
export function parseStrEmpty(str) {
if (!str || str == "undefined" || str == "null") {
return "";
}

View File

@@ -41,7 +41,7 @@
<el-col :sm="24" :lg="12" style="padding-left: 20px">
<h2>若依后台管理框架</h2>
<p>
一直想做一款后台管理系统看了很多优秀的开源项目但是发现没有合适自己的于是利用空闲休息时间开始自己写一套后台系统如此有了若依管理系统她可以用于所有的Web应用程序如网站管理后台网站会员中心CMSCRMOA等等当然您也可以对她进行深度定制以做出更强系统所有前端后台代码封装过后十分精简易上手出错概率低同时支持移动客户端访问系统会陆续更新一些实用功能
一直想做一款后台管理系统看了很多优秀的开源项目但是发现没有合适自己的于是利用空闲休息时间开始自己写一套后台系统如此有了若依管理系统她可以用于所有的Web应用程序如网站管理后台网站会员中心CMSCRMOA等等当然您也可以对她进行深度定制以做出更强系统所有前端后台代码封装过后十分精简易上手出错概率低同时支持移动客户端访问系统会陆续更新一些实用功能
</p>
<p>
<b>当前版本:</b> <span>v{{ version }}</span>
@@ -52,15 +52,13 @@
<p>
<el-button
type="primary"
size="mini"
icon="el-icon-cloudy"
icon="Cloudy"
plain
@click="goTarget('https://gitee.com/y_project/RuoYi-Vue')"
>访问码云</el-button
>
<el-button
size="mini"
icon="el-icon-s-home"
icon="HomeFilled"
plain
@click="goTarget('http://ruoyi.vip')"
>访问主页</el-button
@@ -121,10 +119,10 @@
</p>
<p>
<i class="el-icon-user-solid"></i> QQ群<s>满937441</s>
<s>满887144332</s> <s>满180251782</s> <s>满104180207</s>
<s>186866453</s> <s>201396349</s> <s>满101456076</s>
<a href="https://jq.qq.com/?_wv=1027&k=KmQbXyJ6" target="_blank">
101539465</a
<s>满887144332</s> <s>满180251782</s> <s>满104180207</s> <s>满186866453</s>
<s>201396349</s> <s>101456076</s> <s>满101539465</s> <s>满264312783</s>
<a href="https://jq.qq.com/?_wv=1027&k=SWCtLnMz" target="_blank">
167385320</a
>
</p>
<p>
@@ -151,6 +149,139 @@
</div>
</template>
<el-collapse accordion>
<el-collapse-item title="v3.8.2 - 2022-04-01">
<ol>
<li>前端支持设置是否需要防止数据重复提交</li>
<li>开启TopNav没有子菜单情况隐藏侧边栏</li>
<li>侧边栏菜单名称过长悬停显示标题</li>
<li>用户访问控制时校验数据权限防止越权</li>
<li>导出Excel时屏蔽公式防止CSV注入风险</li>
<li>组件ImagePreview支持多图预览显示</li>
<li>组件ImageUpload支持多图同时选择上传</li>
<li>组件FileUpload支持多文件同时选择上传</li>
<li>服务监控新增运行参数信息显示</li>
<li>定时任务目标字符串过滤特殊字符</li>
<li>定时任务目标字符串验证包名白名单</li>
<li>代码生成列表图片支持预览</li>
<li>代码生成编辑修改打开新页签</li>
<li>代码生成新增Java类型Boolean</li>
<li>代码生成子表支持日期/字典配置</li>
<li>代码生成同步保留必填/类型选项</li>
<li>升级oshi到最新版本6.1.2</li>
<li>升级fastjson到最新版1.2.80</li>
<li>升级pagehelper到最新版1.4.1</li>
<li>升级spring-boot到最新版本2.5.11</li>
<li>升级spring-boot-mybatis到最新版2.2.2</li>
<li>添加遗漏的分页参数合理化属性</li>
<li>修改npm即将过期的注册源地址</li>
<li>修复分页组件请求两次问题</li>
<li>修复通用文件下载接口跨域问题</li>
<li>修复Xss注解字段值为空时的异常问题</li>
<li>修复选项卡点击右键刷新丢失参数问题</li>
<li>修复表单清除元素位置未垂直居中问题</li>
<li>修复服务监控中运行参数显示条件错误</li>
<li>修复导入Excel时字典字段类型为Long转义为空问题</li>
<li>修复登录超时刷新页面跳转登录页面还提示重新登录问题</li>
<li>优化加载字典缓存数据</li>
<li>优化IP地址获取到多个的问题</li>
<li>优化任务队列满时任务拒绝策略</li>
<li>优化文件上传兼容Weblogic环境</li>
<li>优化定时任务默认保存到内存中执行</li>
<li>优化部门修改缩放后出现的错位问题</li>
<li>优化Excel格式化不同类型的日期对象</li>
<li>优化菜单表关键字导致的插件报错问题</li>
<li>优化Oracle用户头像列为空时不显示问题</li>
<li>优化页面若未匹配到字典标签则返回原字典值</li>
<li>优化修复登录失效后多次请求提示多次弹窗问题</li>
<li>其他细节优化</li>
</ol>
</el-collapse-item>
<el-collapse-item title="v3.8.1 - 2022-01-01">
<ol>
<li>新增Vue3前端代码生成模板</li>
<li>新增图片预览组件</li>
<li>新增压缩插件实现打包Gzip</li>
<li>自定义xss校验注解实现</li>
<li>自定义文字复制剪贴指令</li>
<li>代码生成预览支持复制内容</li>
<li>路由支持单独配置菜单或角色权限</li>
<li>用户管理部门查询选择节点后分页参数初始</li>
<li>修复用户分配角色属性错误</li>
<li>修复打包后字体图标偶现的乱码问题</li>
<li>修复菜单管理重置表单出现的错误</li>
<li>修复版本差异导致的懒加载报错问题</li>
<li>修复Cron组件中周回显问题</li>
<li>修复定时任务多参数逗号分隔的问题</li>
<li>修复根据ID查询列表可能出现的主键溢出问题</li>
<li>修复tomcat配置参数已过期问题</li>
<li>升级clipboard到最新版本2.0.8</li>
<li>升级oshi到最新版本v5.8.6</li>
<li>升级fastjson到最新版1.2.79</li>
<li>升级spring-boot到最新版本2.5.8</li>
<li>升级log4j2到2.17.1防止漏洞风险</li>
<li>优化下载解析blob异常提示</li>
<li>优化代码生成字典组重复问题</li>
<li>优化查询用户的角色组&岗位组代码</li>
<li>优化定时任务cron表达式小时设置24</li>
<li>优化用户导入提示溢出则显示滚动条</li>
<li>优化防重复提交标识组合为(key+url+header)</li>
<li>优化分页方法设置成通用方便灵活调用</li>
<li>其他细节优化</li>
</ol>
</el-collapse-item>
<el-collapse-item title="v3.8.0 - 2021-12-01">
<ol>
<li>新增配套并同步的Vue3前端版本</li>
<li>新增通用方法简化模态/缓存/下载/权限/页签使用</li>
<li>优化导出数据/使用通用下载方法</li>
<li>Excel注解支持自定义数据处理器</li>
<li>Excel注解支持导入导出标题信息</li>
<li>Excel导入支持@Excels注解</li>
<li>新增组件data-dict简化数据字典使用</li>
<li>新增Jaxb依赖防止jdk8以上出现的兼容错误</li>
<li>生产环境使用路由懒加载提升页面响应速度</li>
<li>修复五级以上菜单出现的404问题</li>
<li>防重提交注解支持配置间隔时间/提示消息</li>
<li>日志注解新增是否保存响应参数</li>
<li>任务屏蔽违规字符&参数忽略双引号中的逗号</li>
<li>升级SpringBoot到最新版本2.5.6</li>
<li>升级pagehelper到最新版1.4.0</li>
<li>升级spring-boot-mybatis到最新版2.2.0</li>
<li>升级oshi到最新版本v5.8.2</li>
<li>升级druid到最新版1.2.8</li>
<li>升级velocity到最新版本2.3</li>
<li>升级fastjson到最新版1.2.78</li>
<li>升级axios到最新版本0.24.0</li>
<li>升级dart-sass到版本1.32.13</li>
<li>升级core-js到最新版本3.19.1</li>
<li>升级jsencrypt到最新版本3.2.1</li>
<li>升级js-cookie到最新版本3.0.1</li>
<li>升级file-saver到最新版本2.0.5</li>
<li>升级sass-loader到最新版本10.1.1</li>
<li>升级element-ui到最新版本2.15.6</li>
<li>新增sendGet无参请求方法</li>
<li>禁用el-tag组件的渐变动画</li>
<li>代码生成点击预览重置激活tab</li>
<li>AjaxResult重写put方法以方便链式调用</li>
<li>优化登录/验证码请求headers不设置token</li>
<li>优化用户个人信息接口防止修改用户名</li>
<li>优化Cron表达式生成器关闭时销毁避免缓存</li>
<li>优化注册成功提示消息类型success</li>
<li>优化aop语法使用spring自动注入注解</li>
<li>优化记录登录信息移除不必要的修改</li>
<li>优化mybatis全局默认的执行器</li>
<li>优化Excel导入图片可能出现的异常</li>
<li>修复代码生成模板主子表删除缺少事务</li>
<li>修复日志记录可能出现的转换异常</li>
<li>修复代码生成复选框字典遗漏问题</li>
<li>修复关闭xss功能导致可重复读RepeatableFilter失效</li>
<li>修复字符串无法被反转义问题</li>
<li>修复后端主子表代码模板方法名生成错误问题</li>
<li>修复xss过滤后格式出现的异常</li>
<li>修复swagger没有指定dataTypeClass导致启动出现warn日志</li>
<li>其他细节优化</li>
</ol>
</el-collapse-item>
<el-collapse-item title="v3.7.0 - 2021-09-13">
<ol>
<li>参数管理支持配置验证码开关</li>
@@ -665,7 +796,7 @@
</template>
<script setup name="Index">
const version = ref('3.7.0')
const version = ref('3.8.2')
function goTarget(url) {
window.open(url, '__blank')

View File

@@ -6,6 +6,7 @@
<el-input
v-model="loginForm.username"
type="text"
size="large"
auto-complete="off"
placeholder="账号"
>
@@ -16,6 +17,7 @@
<el-input
v-model="loginForm.password"
type="password"
size="large"
auto-complete="off"
placeholder="密码"
@keyup.enter="handleLogin"
@@ -26,6 +28,7 @@
<el-form-item prop="code" v-if="captchaOnOff">
<el-input
v-model="loginForm.code"
size="large"
auto-complete="off"
placeholder="验证码"
style="width: 63%"
@@ -41,7 +44,7 @@
<el-form-item style="width:100%;">
<el-button
:loading="loading"
size="medium"
size="large"
type="primary"
style="width:100%;"
@click.prevent="handleLogin"
@@ -56,7 +59,7 @@
</el-form>
<!-- 底部 -->
<div class="el-login-footer">
<span>Copyright © 2018-2021 ruoyi.vip All Rights Reserved.</span>
<span>Copyright © 2018-2022 ruoyi.vip All Rights Reserved.</span>
</div>
</div>
</template>
@@ -167,15 +170,15 @@ getCookie();
width: 400px;
padding: 25px 25px 5px 25px;
.el-input {
height: 38px;
height: 40px;
input {
height: 38px;
height: 40px;
}
}
.input-icon {
height: 39px;
width: 14px;
margin-left: 2px;
margin-left: 0px;
}
}
.login-tip {
@@ -185,7 +188,7 @@ getCookie();
}
.login-code {
width: 33%;
height: 38px;
height: 40px;
float: right;
img {
cursor: pointer;
@@ -205,6 +208,7 @@ getCookie();
letter-spacing: 1px;
}
.login-code-img {
height: 38px;
height: 40px;
padding-left: 12px;
}
</style>

View File

@@ -9,5 +9,5 @@ import iFrame from '@/components/iFrame'
import { ref } from 'vue';
const url = ref(import.meta.env.VITE_APP_BASE_API + 'druid/login.html');
const url = ref(import.meta.env.VITE_APP_BASE_API + '/druid/login.html');
</script>

View File

@@ -6,7 +6,6 @@
v-model="queryParams.jobName"
placeholder="请输入任务名称"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
@@ -31,8 +30,8 @@
</el-select>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -42,7 +41,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="handleAdd"
v-hasPermi="['monitor:job:add']"
>新增</el-button>
@@ -52,7 +50,6 @@
type="success"
plain
icon="Edit"
size="mini"
:disabled="single"
@click="handleUpdate"
v-hasPermi="['monitor:job:edit']"
@@ -63,7 +60,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['monitor:job:remove']"
@@ -74,7 +70,6 @@
type="warning"
plain
icon="Download"
size="mini"
@click="handleExport"
v-hasPermi="['monitor:job:export']"
>导出</el-button>
@@ -84,7 +79,6 @@
type="info"
plain
icon="Operation"
size="mini"
@click="handleJobLog"
v-hasPermi="['monitor:job:query']"
>日志</el-button>
@@ -115,35 +109,46 @@
</el-table-column>
<el-table-column label="操作" align="center" width="200" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['monitor:job:edit']"
>修改</el-button>
<el-button
size="mini"
type="text"
icon="Delete"
@click="handleDelete(scope.row)"
v-hasPermi="['monitor:job:remove']"
>删除</el-button>
<el-dropdown size="mini" @command="(command) => handleCommand(command, scope.row)">
<span class="el-dropdown-link" v-hasPermi="['monitor:job:changeStatus', 'monitor:job:query']">
<i class="el-icon-d-arrow-right el-icon--right"></i>更多
</span>
<template #dropdown>
<el-dropdown-menu>
<el-dropdown-item command="handleRun" icon="CaretRight"
v-hasPermi="['monitor:job:changeStatus']">执行一次</el-dropdown-item>
<el-dropdown-item command="handleView" icon="View"
v-hasPermi="['monitor:job:query']">任务详细</el-dropdown-item>
<el-dropdown-item command="handleJobLog" icon="Operation"
v-hasPermi="['monitor:job:query']">调度日志</el-dropdown-item>
</el-dropdown-menu>
</template>
</el-dropdown>
<el-tooltip content="修改" placement="top">
<el-button
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['monitor:job:edit']"
></el-button>
</el-tooltip>
<el-tooltip content="删除" placement="top">
<el-button
type="text"
icon="Delete"
@click="handleDelete(scope.row)"
v-hasPermi="['monitor:job:remove']"
></el-button>
</el-tooltip>
<el-tooltip content="执行一次" placement="top">
<el-button
type="text"
icon="CaretRight"
@click="handleRun(scope.row)"
v-hasPermi="['monitor:job:changeStatus']"
></el-button>
</el-tooltip>
<el-tooltip content="任务详细" placement="top">
<el-button
type="text"
icon="View"
@click="handleView(scope.row)"
v-hasPermi="['monitor:job:query']"
></el-button>
</el-tooltip>
<el-tooltip content="调度日志" placement="top">
<el-button
type="text"
icon="Operation"
@click="handleJobLog(scope.row)"
v-hasPermi="['monitor:job:query']"
></el-button>
</el-tooltip>
</template>
</el-table-column>
</el-table>
@@ -210,8 +215,8 @@
</el-form-item>
</el-col>
<el-col :span="24">
<el-form-item label="错误策略" prop="misfirePolicy">
<el-radio-group v-model="form.misfirePolicy" size="small">
<el-form-item label="执行策略" prop="misfirePolicy">
<el-radio-group v-model="form.misfirePolicy">
<el-radio-button label="1">立即执行</el-radio-button>
<el-radio-button label="2">执行一次</el-radio-button>
<el-radio-button label="3">放弃执行</el-radio-button>
@@ -220,7 +225,7 @@
</el-col>
<el-col :span="12">
<el-form-item label="是否并发" prop="concurrent">
<el-radio-group v-model="form.concurrent" size="small">
<el-radio-group v-model="form.concurrent">
<el-radio-button label="0">允许</el-radio-button>
<el-radio-button label="1">禁止</el-radio-button>
</el-radio-group>
@@ -249,7 +254,7 @@
<!-- 任务日志详细 -->
<el-dialog title="任务详细" v-model="openView" width="700px" append-to-body>
<el-form :model="form" label-width="120px" size="mini">
<el-form :model="form" label-width="120px">
<el-row>
<el-col :span="12">
<el-form-item label="任务编号:">{{ form.jobId }}</el-form-item>
@@ -348,7 +353,7 @@ function getList() {
}
/** 任务组名字典翻译 */
function jobGroupFormat(row, column) {
return proxy.selectDictLabel(sys_job_group, row.jobGroup);
return proxy.selectDictLabel(sys_job_group.value, row.jobGroup);
}
/** 取消按钮 */
function cancel() {

View File

@@ -6,7 +6,6 @@
v-model="queryParams.jobName"
placeholder="请输入任务名称"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
@@ -14,9 +13,8 @@
<el-form-item label="任务组名" prop="jobGroup">
<el-select
v-model="queryParams.jobGroup"
placeholder="请任务组名"
placeholder="请选择任务组名"
clearable
size="small"
style="width: 240px"
>
<el-option
@@ -32,7 +30,6 @@
v-model="queryParams.status"
placeholder="请选择执行状态"
clearable
size="small"
style="width: 240px"
>
<el-option
@@ -43,11 +40,9 @@
/>
</el-select>
</el-form-item>
<el-form-item label="执行时间">
<el-form-item label="执行时间" style="width: 308px">
<el-date-picker
v-model="dateRange"
size="small"
style="width: 240px"
value-format="YYYY-MM-DD"
type="daterange"
range-separator="-"
@@ -56,8 +51,8 @@
></el-date-picker>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -67,7 +62,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['monitor:job:remove']"
@@ -78,7 +72,6 @@
type="danger"
plain
icon="Delete"
size="mini"
@click="handleClean"
v-hasPermi="['monitor:job:remove']"
>清空</el-button>
@@ -88,7 +81,6 @@
type="warning"
plain
icon="Download"
size="mini"
@click="handleExport"
v-hasPermi="['monitor:job:export']"
>导出</el-button>
@@ -98,7 +90,6 @@
type="warning"
plain
icon="Close"
size="mini"
@click="handleClose"
>关闭</el-button>
</el-col>
@@ -129,7 +120,6 @@
<el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="View"
@click="handleView(scope.row)"
@@ -149,7 +139,7 @@
<!-- 调度日志详细 -->
<el-dialog title="调度日志详细" v-model="open" width="700px" append-to-body>
<el-form :model="form" label-width="100px" size="mini">
<el-form :model="form" label-width="100px">
<el-row>
<el-col :span="12">
<el-form-item label="日志序号:">{{ form.jobLogId }}</el-form-item>

View File

@@ -6,7 +6,6 @@
v-model="queryParams.ipaddr"
placeholder="请输入登录地址"
clearable
size="small"
style="width: 240px;"
@keyup.enter="handleQuery"
/>
@@ -16,7 +15,6 @@
v-model="queryParams.userName"
placeholder="请输入用户名称"
clearable
size="small"
style="width: 240px;"
@keyup.enter="handleQuery"
/>
@@ -26,7 +24,6 @@
v-model="queryParams.status"
placeholder="登录状态"
clearable
size="small"
style="width: 240px"
>
<el-option
@@ -37,11 +34,9 @@
/>
</el-select>
</el-form-item>
<el-form-item label="登录时间">
<el-form-item label="登录时间" style="width: 308px">
<el-date-picker
v-model="dateRange"
size="small"
style="width: 240px"
value-format="YYYY-MM-DD"
type="daterange"
range-separator="-"
@@ -50,8 +45,8 @@
></el-date-picker>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -61,7 +56,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['system:logininfor:remove']"
@@ -72,7 +66,6 @@
type="danger"
plain
icon="Delete"
size="mini"
@click="handleClean"
v-hasPermi="['system:logininfor:remove']"
>清空</el-button>
@@ -82,7 +75,6 @@
type="warning"
plain
icon="Download"
size="mini"
@click="handleExport"
v-hasPermi="['system:logininfor:export']"
>导出</el-button>

View File

@@ -6,7 +6,6 @@
v-model="queryParams.ipaddr"
placeholder="请输入登录地址"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
@@ -19,8 +18,8 @@
/>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
<el-table
@@ -28,7 +27,7 @@
:data="onlineList.slice((pageNum - 1) * pageSize, pageNum * pageSize)"
style="width: 100%;"
>
<el-table-column label="序号" type="index" align="center">
<el-table-column label="序号" width="50" type="index" align="center">
<template #default="scope">
<span>{{ (pageNum - 1) * pageSize + scope.$index + 1 }}</span>
</template>
@@ -48,7 +47,6 @@
<el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="Delete"
@click="handleForceLogout(scope.row)"
@@ -99,7 +97,6 @@ function resetQuery() {
}
/** 强退按钮操作 */
function handleForceLogout(row) {
const operIds = row.operId || ids.value;
proxy.$modal.confirm('是否确认强退名称为"' + row.userName + '"的用户?').then(function () {
return forceLogout(row.tokenId);
}).then(() => {

View File

@@ -6,7 +6,6 @@
v-model="queryParams.title"
placeholder="请输入系统模块"
clearable
size="small"
style="width: 240px;"
@keyup.enter="handleQuery"
/>
@@ -16,7 +15,6 @@
v-model="queryParams.operName"
placeholder="请输入操作人员"
clearable
size="small"
style="width: 240px;"
@keyup.enter="handleQuery"
/>
@@ -26,7 +24,6 @@
v-model="queryParams.businessType"
placeholder="操作类型"
clearable
size="small"
style="width: 240px"
>
<el-option
@@ -42,7 +39,6 @@
v-model="queryParams.status"
placeholder="操作状态"
clearable
size="small"
style="width: 240px"
>
<el-option
@@ -53,11 +49,9 @@
/>
</el-select>
</el-form-item>
<el-form-item label="操作时间">
<el-form-item label="操作时间" style="width: 308px">
<el-date-picker
v-model="dateRange"
size="small"
style="width: 240px"
value-format="YYYY-MM-DD"
type="daterange"
range-separator="-"
@@ -66,8 +60,8 @@
></el-date-picker>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -77,7 +71,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['system:operlog:remove']"
@@ -88,7 +81,6 @@
type="danger"
plain
icon="Delete"
size="mini"
@click="handleClean"
v-hasPermi="['system:operlog:remove']"
>清空</el-button>
@@ -98,7 +90,6 @@
type="warning"
plain
icon="Download"
size="mini"
@click="handleExport"
v-hasPermi="['system:operlog:export']"
>导出</el-button>
@@ -131,7 +122,6 @@
<el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="View"
@click="handleView(scope.row, scope.index)"
@@ -151,7 +141,7 @@
<!-- 操作日志详细 -->
<el-dialog title="操作日志详细" v-model="open" width="700px" append-to-body>
<el-form :model="form" label-width="100px" size="mini">
<el-form :model="form" label-width="100px">
<el-row>
<el-col :span="12">
<el-form-item label="操作模块:">{{ form.title }} / {{ typeFormat(form) }}</el-form-item>
@@ -238,7 +228,7 @@ function getList() {
}
/** 操作日志类型字典翻译 */
function typeFormat(row, column) {
return selectDictLabel(sys_oper_type, row.businessType);
return proxy.selectDictLabel(sys_oper_type.value, row.businessType);
}
/** 搜索按钮操作 */
function handleQuery() {

View File

@@ -124,6 +124,10 @@
<td colspan="1" class="el-table__cell is-leaf"><div class="cell">项目路径</div></td>
<td colspan="3" class="el-table__cell is-leaf"><div class="cell" v-if="server.sys">{{ server.sys.userDir }}</div></td>
</tr>
<tr>
<td colspan="1" class="el-table__cell is-leaf"><div class="cell">运行参数</div></td>
<td colspan="3" class="el-table__cell is-leaf"><div class="cell" v-if="server.jvm">{{ server.jvm.inputArgs }}</div></td>
</tr>
</tbody>
</table>
</div>

View File

@@ -3,7 +3,13 @@
<el-form ref="registerRef" :model="registerForm" :rules="registerRules" class="register-form">
<h3 class="title">若依后台管理系统</h3>
<el-form-item prop="username">
<el-input v-model="registerForm.username" type="text" auto-complete="off" placeholder="账号">
<el-input
v-model="registerForm.username"
type="text"
size="large"
auto-complete="off"
placeholder="账号"
>
<template #prefix><svg-icon icon-class="user" class="el-input__icon input-icon" /></template>
</el-input>
</el-form-item>
@@ -11,6 +17,7 @@
<el-input
v-model="registerForm.password"
type="password"
size="large"
auto-complete="off"
placeholder="密码"
@keyup.enter="handleRegister"
@@ -22,6 +29,7 @@
<el-input
v-model="registerForm.confirmPassword"
type="password"
size="large"
auto-complete="off"
placeholder="确认密码"
@keyup.enter="handleRegister"
@@ -31,6 +39,7 @@
</el-form-item>
<el-form-item prop="code" v-if="captchaOnOff">
<el-input
size="large"
v-model="registerForm.code"
auto-complete="off"
placeholder="验证码"
@@ -46,7 +55,7 @@
<el-form-item style="width:100%;">
<el-button
:loading="loading"
size="medium"
size="large"
type="primary"
style="width:100%;"
@click.prevent="handleRegister"
@@ -61,7 +70,7 @@
</el-form>
<!-- 底部 -->
<div class="el-register-footer">
<span>Copyright © 2018-2021 ruoyi.vip All Rights Reserved.</span>
<span>Copyright © 2018-2022 ruoyi.vip All Rights Reserved.</span>
</div>
</div>
</template>
@@ -165,15 +174,15 @@ getCode();
width: 400px;
padding: 25px 25px 5px 25px;
.el-input {
height: 38px;
height: 40px;
input {
height: 38px;
height: 40px;
}
}
.input-icon {
height: 39px;
width: 14px;
margin-left: 2px;
margin-left: 0px;
}
}
.register-tip {
@@ -183,7 +192,7 @@ getCode();
}
.register-code {
width: 33%;
height: 38px;
height: 40px;
float: right;
img {
cursor: pointer;
@@ -203,6 +212,7 @@ getCode();
letter-spacing: 1px;
}
.register-code-img {
height: 38px;
height: 40px;
padding-left: 12px;
}
</style>

View File

@@ -6,7 +6,6 @@
v-model="queryParams.configName"
placeholder="请输入参数名称"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
@@ -16,13 +15,12 @@
v-model="queryParams.configKey"
placeholder="请输入参数键名"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
</el-form-item>
<el-form-item label="系统内置" prop="configType">
<el-select v-model="queryParams.configType" placeholder="系统内置" clearable size="small">
<el-select v-model="queryParams.configType" placeholder="系统内置" clearable>
<el-option
v-for="dict in sys_yes_no"
:key="dict.value"
@@ -31,11 +29,9 @@
/>
</el-select>
</el-form-item>
<el-form-item label="创建时间">
<el-form-item label="创建时间" style="width: 308px;">
<el-date-picker
v-model="dateRange"
size="small"
style="width: 240px"
value-format="YYYY-MM-DD"
type="daterange"
range-separator="-"
@@ -44,8 +40,8 @@
></el-date-picker>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -55,7 +51,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="handleAdd"
v-hasPermi="['system:config:add']"
>新增</el-button>
@@ -65,7 +60,6 @@
type="success"
plain
icon="Edit"
size="mini"
:disabled="single"
@click="handleUpdate"
v-hasPermi="['system:config:edit']"
@@ -76,7 +70,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['system:config:remove']"
@@ -87,7 +80,6 @@
type="warning"
plain
icon="Download"
size="mini"
@click="handleExport"
v-hasPermi="['system:config:export']"
>导出</el-button>
@@ -97,7 +89,6 @@
type="danger"
plain
icon="Refresh"
size="mini"
@click="handleRefreshCache"
v-hasPermi="['system:config:remove']"
>刷新缓存</el-button>
@@ -125,14 +116,12 @@
<el-table-column label="操作" align="center" width="150" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['system:config:edit']"
>修改</el-button>
<el-button
size="mini"
type="text"
icon="Delete"
@click="handleDelete(scope.row)"

View File

@@ -6,12 +6,11 @@
v-model="queryParams.deptName"
placeholder="请输入部门名称"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
<el-form-item label="状态" prop="status">
<el-select v-model="queryParams.status" placeholder="部门状态" clearable size="small">
<el-select v-model="queryParams.status" placeholder="部门状态" clearable>
<el-option
v-for="dict in sys_normal_disable"
:key="dict.value"
@@ -21,8 +20,8 @@
</el-select>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -32,7 +31,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="handleAdd"
v-hasPermi="['system:dept:add']"
>新增</el-button>
@@ -42,7 +40,6 @@
type="info"
plain
icon="Sort"
size="mini"
@click="toggleExpandAll"
>展开/折叠</el-button>
</el-col>
@@ -72,14 +69,12 @@
<el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['system:dept:edit']"
>修改</el-button>
<el-button
size="mini"
type="text"
icon="Plus"
@click="handleAdd(scope.row)"
@@ -87,7 +82,6 @@
>新增</el-button>
<el-button
v-if="scope.row.parentId != 0"
size="mini"
type="text"
icon="Delete"
@click="handleDelete(scope.row)"
@@ -184,7 +178,7 @@ const data = reactive({
parentId: [{ required: true, message: "上级部门不能为空", trigger: "blur" }],
deptName: [{ required: true, message: "部门名称不能为空", trigger: "blur" }],
orderNum: [{ required: true, message: "显示排序不能为空", trigger: "blur" }],
email: [{ type: "email", message: "'请输入正确的邮箱地址", trigger: ["blur", "change"] }],
email: [{ type: "email", message: "请输入正确的邮箱地址", trigger: ["blur", "change"] }],
phone: [{ pattern: /^1[3|4|5|6|7|8|9][0-9]\d{8}$/, message: "请输入正确的手机号码", trigger: "blur" }]
},
});

View File

@@ -2,7 +2,7 @@
<div class="app-container">
<el-form :model="queryParams" ref="queryRef" :inline="true" v-show="showSearch" label-width="68px">
<el-form-item label="字典名称" prop="dictType">
<el-select v-model="queryParams.dictType" size="small">
<el-select v-model="queryParams.dictType">
<el-option
v-for="item in typeOptions"
:key="item.dictId"
@@ -16,12 +16,11 @@
v-model="queryParams.dictLabel"
placeholder="请输入字典标签"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
<el-form-item label="状态" prop="status">
<el-select v-model="queryParams.status" placeholder="数据状态" clearable size="small">
<el-select v-model="queryParams.status" placeholder="数据状态" clearable>
<el-option
v-for="dict in sys_normal_disable"
:key="dict.value"
@@ -31,8 +30,8 @@
</el-select>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -42,7 +41,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="handleAdd"
v-hasPermi="['system:dict:add']"
>新增</el-button>
@@ -52,7 +50,6 @@
type="success"
plain
icon="Edit"
size="mini"
:disabled="single"
@click="handleUpdate"
v-hasPermi="['system:dict:edit']"
@@ -63,7 +60,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['system:dict:remove']"
@@ -74,7 +70,6 @@
type="warning"
plain
icon="Download"
size="mini"
@click="handleExport"
v-hasPermi="['system:dict:export']"
>导出</el-button>
@@ -84,7 +79,6 @@
type="warning"
plain
icon="Close"
size="mini"
@click="handleClose"
>关闭</el-button>
</el-col>
@@ -116,14 +110,12 @@
<el-table-column label="操作" align="center" width="150" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['system:dict:edit']"
>修改</el-button>
<el-button
size="mini"
type="text"
icon="Delete"
@click="handleDelete(scope.row)"

View File

@@ -6,7 +6,6 @@
v-model="queryParams.dictName"
placeholder="请输入字典名称"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
@@ -16,7 +15,6 @@
v-model="queryParams.dictType"
placeholder="请输入字典类型"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
@@ -26,7 +24,6 @@
v-model="queryParams.status"
placeholder="字典状态"
clearable
size="small"
style="width: 240px"
>
<el-option
@@ -37,11 +34,9 @@
/>
</el-select>
</el-form-item>
<el-form-item label="创建时间">
<el-form-item label="创建时间" style="width: 308px">
<el-date-picker
v-model="dateRange"
size="small"
style="width: 240px"
value-format="YYYY-MM-DD"
type="daterange"
range-separator="-"
@@ -50,8 +45,8 @@
></el-date-picker>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -61,7 +56,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="handleAdd"
v-hasPermi="['system:dict:add']"
>新增</el-button>
@@ -71,7 +65,6 @@
type="success"
plain
icon="Edit"
size="mini"
:disabled="single"
@click="handleUpdate"
v-hasPermi="['system:dict:edit']"
@@ -82,7 +75,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['system:dict:remove']"
@@ -93,7 +85,6 @@
type="warning"
plain
icon="Download"
size="mini"
@click="handleExport"
v-hasPermi="['system:dict:export']"
>导出</el-button>
@@ -103,7 +94,6 @@
type="danger"
plain
icon="Refresh"
size="mini"
@click="handleRefreshCache"
v-hasPermi="['system:dict:remove']"
>刷新缓存</el-button>
@@ -136,14 +126,12 @@
<el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['system:dict:edit']"
>修改</el-button>
<el-button
size="mini"
type="text"
icon="Delete"
@click="handleDelete(scope.row)"

View File

@@ -6,12 +6,11 @@
v-model="queryParams.menuName"
placeholder="请输入菜单名称"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
<el-form-item label="状态" prop="status">
<el-select v-model="queryParams.status" placeholder="菜单状态" clearable size="small">
<el-select v-model="queryParams.status" placeholder="菜单状态" clearable>
<el-option
v-for="dict in sys_normal_disable"
:key="dict.value"
@@ -21,8 +20,8 @@
</el-select>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -32,7 +31,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="handleAdd"
v-hasPermi="['system:menu:add']"
>新增</el-button>
@@ -42,7 +40,6 @@
type="info"
plain
icon="Sort"
size="mini"
@click="toggleExpandAll"
>展开/折叠</el-button>
</el-col>
@@ -79,21 +76,18 @@
<el-table-column label="操作" align="center" width="200" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['system:menu:edit']"
>修改</el-button>
<el-button
size="mini"
type="text"
icon="Plus"
@click="handleAdd(scope.row)"
v-hasPermi="['system:menu:add']"
>新增</el-button>
<el-button
size="mini"
type="text"
icon="Delete"
@click="handleDelete(scope.row)"
@@ -104,7 +98,7 @@
</el-table>
<!-- 添加或修改菜单对话框 -->
<el-dialog :title="title" v-model="open" width="680px" append-to-body>
<el-dialog :title="title" v-model="open" width="680px" :before-close="handleClose" append-to-body>
<el-form ref="menuRef" :model="form" :rules="rules" label-width="100px">
<el-row>
<el-col :span="24">
@@ -127,7 +121,7 @@
</el-form-item>
</el-col>
<el-col :span="24" v-if="form.menuType != 'F'">
<el-form-item label="菜单图标">
<el-form-item label="菜单图标" prop="icon">
<el-popover
placement="bottom-start"
:width="540"
@@ -135,9 +129,8 @@
trigger="click"
@show="showSelectIcon"
>
<icon-select ref="iconSelectRef" @selected="selected" />
<template #reference>
<el-input v-model="form.icon" placeholder="点击选择图标" readonly>
<el-input v-model="form.icon" placeholder="点击选择图标" @click="showSelectIcon" readonly>
<template #prefix>
<svg-icon
v-if="form.icon"
@@ -145,10 +138,11 @@
class="el-input__icon"
style="height: 32px;width: 16px;"
/>
<i v-else class="el-icon-search el-input__icon" />
<el-icon v-else style="height: 32px;width: 16px;"><search /></el-icon>
</template>
</el-input>
</template>
<icon-select ref="iconSelectRef" @selected="selected" />
</el-popover>
</el-form-item>
</el-col>
@@ -377,6 +371,11 @@ function selected(name) {
form.value.icon = name;
showChooseIcon.value = false;
}
/** 关闭弹窗隐藏图标选择 */
function handleClose() {
cancel();
showChooseIcon.value = false;
}
/** 搜索按钮操作 */
function handleQuery() {
getList();

View File

@@ -6,7 +6,6 @@
v-model="queryParams.noticeTitle"
placeholder="请输入公告标题"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
@@ -19,7 +18,7 @@
/>
</el-form-item>
<el-form-item label="类型" prop="noticeType">
<el-select v-model="queryParams.noticeType" placeholder="公告类型" clearable size="small">
<el-select v-model="queryParams.noticeType" placeholder="公告类型" clearable>
<el-option
v-for="dict in sys_notice_type"
:key="dict.value"
@@ -29,8 +28,8 @@
</el-select>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -40,7 +39,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="handleAdd"
v-hasPermi="['system:notice:add']"
>新增</el-button>
@@ -50,7 +48,6 @@
type="success"
plain
icon="Edit"
size="mini"
:disabled="single"
@click="handleUpdate"
v-hasPermi="['system:notice:edit']"
@@ -61,7 +58,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['system:notice:remove']"
@@ -98,14 +94,12 @@
<el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['system:notice:edit']"
>修改</el-button>
<el-button
size="mini"
type="text"
icon="Delete"
@click="handleDelete(scope.row)"

View File

@@ -6,7 +6,6 @@
v-model="queryParams.postCode"
placeholder="请输入岗位编码"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
@@ -15,12 +14,11 @@
v-model="queryParams.postName"
placeholder="请输入岗位名称"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
<el-form-item label="状态" prop="status">
<el-select v-model="queryParams.status" placeholder="岗位状态" clearable size="small">
<el-select v-model="queryParams.status" placeholder="岗位状态" clearable>
<el-option
v-for="dict in sys_normal_disable"
:key="dict.value"
@@ -30,8 +28,8 @@
</el-select>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -41,7 +39,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="handleAdd"
v-hasPermi="['system:post:add']"
>新增</el-button>
@@ -51,7 +48,6 @@
type="success"
plain
icon="Edit"
size="mini"
:disabled="single"
@click="handleUpdate"
v-hasPermi="['system:post:edit']"
@@ -62,7 +58,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['system:post:remove']"
@@ -73,7 +68,6 @@
type="warning"
plain
icon="Download"
size="mini"
@click="handleExport"
v-hasPermi="['system:post:export']"
>导出</el-button>
@@ -100,14 +94,12 @@
<el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['system:post:edit']"
>修改</el-button>
<el-button
size="mini"
type="text"
icon="Delete"
@click="handleDelete(scope.row)"

View File

@@ -7,7 +7,6 @@
v-model="queryParams.userName"
placeholder="请输入用户名称"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
@@ -17,14 +16,13 @@
v-model="queryParams.phonenumber"
placeholder="请输入手机号码"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -34,7 +32,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="openSelectUser"
v-hasPermi="['system:role:add']"
>添加用户</el-button>
@@ -44,7 +41,6 @@
type="danger"
plain
icon="CircleClose"
size="mini"
:disabled="multiple"
@click="cancelAuthUserAll"
v-hasPermi="['system:role:remove']"
@@ -55,7 +51,6 @@
type="warning"
plain
icon="Close"
size="mini"
@click="handleClose"
>关闭</el-button>
</el-col>
@@ -81,7 +76,6 @@
<el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
type="text"
icon="CircleClose"
@click="cancelAuthUser(scope.row)"

View File

@@ -6,7 +6,6 @@
v-model="queryParams.roleName"
placeholder="请输入角色名称"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
@@ -16,7 +15,6 @@
v-model="queryParams.roleKey"
placeholder="请输入权限字符"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
@@ -26,7 +24,6 @@
v-model="queryParams.status"
placeholder="角色状态"
clearable
size="small"
style="width: 240px"
>
<el-option
@@ -37,11 +34,9 @@
/>
</el-select>
</el-form-item>
<el-form-item label="创建时间">
<el-form-item label="创建时间" style="width: 308px">
<el-date-picker
v-model="dateRange"
size="small"
style="width: 240px"
value-format="YYYY-MM-DD"
type="daterange"
range-separator="-"
@@ -50,8 +45,8 @@
></el-date-picker>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
<el-row :gutter="10" class="mb8">
@@ -60,7 +55,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="handleAdd"
v-hasPermi="['system:role:add']"
>新增</el-button>
@@ -70,7 +64,6 @@
type="success"
plain
icon="Edit"
size="mini"
:disabled="single"
@click="handleUpdate"
v-hasPermi="['system:role:edit']"
@@ -81,7 +74,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['system:role:remove']"
@@ -92,7 +84,6 @@
type="warning"
plain
icon="Download"
size="mini"
@click="handleExport"
v-hasPermi="['system:role:export']"
>导出</el-button>
@@ -117,42 +108,45 @@
></el-switch>
</template>
</el-table-column>
<el-table-column label="创建时间" align="center" prop="createTime" width="180">
<el-table-column label="创建时间" align="center" prop="createTime">
<template #default="scope">
<span>{{ parseTime(scope.row.createTime) }}</span>
</template>
</el-table-column>
<el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
v-if="scope.row.roleId !== 1"
<el-tooltip content="修改" placement="top" v-if="scope.row.roleId !== 1">
<el-button
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['system:role:edit']"
>修改</el-button>
<el-button
size="mini"
v-if="scope.row.roleId !== 1"
></el-button>
</el-tooltip>
<el-tooltip content="删除" placement="top" v-if="scope.row.roleId !== 1">
<el-button
type="text"
icon="Delete"
@click="handleDelete(scope.row)"
v-hasPermi="['system:role:remove']"
>删除</el-button>
<el-dropdown size="mini" v-if="scope.row.roleId !== 1" @command="(command) => handleCommand(command, scope.row)">
<span class="el-dropdown-link" v-hasPermi="['system:role:edit']">
<el-icon><d-arrow-right /></el-icon>更多
</span>
<template #dropdown>
<el-dropdown-menu>
<el-dropdown-item command="handleDataScope" icon="CircleCheck"
v-hasPermi="['system:role:edit']">数据权限</el-dropdown-item>
<el-dropdown-item command="handleAuthUser" icon="User"
v-hasPermi="['system:role:edit']">分配用户</el-dropdown-item>
</el-dropdown-menu>
</template>
</el-dropdown>
></el-button>
</el-tooltip>
<el-tooltip content="数据权限" placement="top" v-if="scope.row.roleId !== 1">
<el-button
type="text"
icon="CircleCheck"
@click="handleDataScope(scope.row)"
v-hasPermi="['system:role:edit']"
></el-button>
</el-tooltip>
<el-tooltip content="分配用户" placement="top" v-if="scope.row.roleId !== 1">
<el-button
type="text"
icon="User"
@click="handleAuthUser(scope.row)"
v-hasPermi="['system:role:edit']"
></el-button>
</el-tooltip>
</template>
</el-table-column>
</el-table>

View File

@@ -7,7 +7,6 @@
v-model="queryParams.userName"
placeholder="请输入用户名称"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
@@ -16,13 +15,12 @@
v-model="queryParams.phonenumber"
placeholder="请输入手机号码"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
<el-row>

View File

@@ -9,7 +9,7 @@
</el-form-item>
</el-col>
<el-col :span="8" :offset="2">
<el-form-item label="登录账号" prop="phonenumber">
<el-form-item label="登录账号" prop="userName">
<el-input v-model="form.userName" disabled />
</el-form-item>
</el-col>
@@ -18,7 +18,7 @@
<h4 class="form-header h4">角色信息</h4>
<el-table v-loading="loading" :row-key="getRowKey" @row-click="clickRow" ref="roleRef" @selection-change="handleSelectionChange" :data="roles.slice((pageNum - 1) * pageSize, pageNum * pageSize)">
<el-table-column label="序号" type="index" align="center">
<el-table-column label="序号" width="55" type="index" align="center">
<template #default="scope">
<span>{{ (pageNum - 1) * pageSize + scope.$index + 1 }}</span>
</template>
@@ -37,10 +37,10 @@
<pagination v-show="total > 0" :total="total" v-model:page="pageNum" v-model:limit="pageSize" />
<el-form label-width="100px">
<el-form-item style="text-align: center;margin-left:-120px;margin-top:30px;">
<div style="text-align: center;margin-left:-120px;margin-top:30px;">
<el-button type="primary" @click="submitForm()">提交</el-button>
<el-button @click="close()">返回</el-button>
</el-form-item>
</div>
</el-form>
</div>
</template>

View File

@@ -8,8 +8,7 @@
v-model="deptName"
placeholder="请输入部门名称"
clearable
size="small"
prefix-icon="el-icon-search"
prefix-icon="Search"
style="margin-bottom: 20px"
/>
</div>
@@ -33,7 +32,6 @@
v-model="queryParams.userName"
placeholder="请输入用户名称"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
@@ -43,7 +41,6 @@
v-model="queryParams.phonenumber"
placeholder="请输入手机号码"
clearable
size="small"
style="width: 240px"
@keyup.enter="handleQuery"
/>
@@ -53,7 +50,6 @@
v-model="queryParams.status"
placeholder="用户状态"
clearable
size="small"
style="width: 240px"
>
<el-option
@@ -64,11 +60,9 @@
/>
</el-select>
</el-form-item>
<el-form-item label="创建时间">
<el-form-item label="创建时间" style="width: 308px;">
<el-date-picker
v-model="dateRange"
size="small"
style="width: 240px"
value-format="YYYY-MM-DD"
type="daterange"
range-separator="-"
@@ -77,8 +71,8 @@
></el-date-picker>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -88,7 +82,6 @@
type="primary"
plain
icon="Plus"
size="mini"
@click="handleAdd"
v-hasPermi="['system:user:add']"
>新增</el-button>
@@ -98,7 +91,6 @@
type="success"
plain
icon="Edit"
size="mini"
:disabled="single"
@click="handleUpdate"
v-hasPermi="['system:user:edit']"
@@ -109,7 +101,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['system:user:remove']"
@@ -120,7 +111,6 @@
type="info"
plain
icon="Upload"
size="mini"
@click="handleImport"
v-hasPermi="['system:user:import']"
>导入</el-button>
@@ -130,7 +120,6 @@
type="warning"
plain
icon="Download"
size="mini"
@click="handleExport"
v-hasPermi="['system:user:export']"
>导出</el-button>
@@ -155,42 +144,45 @@
></el-switch>
</template>
</el-table-column>
<el-table-column label="创建时间" align="center" prop="createTime" v-if="columns[6].visible" width="150">
<el-table-column label="创建时间" align="center" prop="createTime" v-if="columns[6].visible" width="160">
<template #default="scope">
<span>{{ parseTime(scope.row.createTime) }}</span>
</template>
</el-table-column>
<el-table-column label="操作" align="center" width="180" class-name="small-padding fixed-width">
<el-table-column label="操作" align="center" width="150" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
size="mini"
v-if="scope.row.userId !== 1"
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['system:user:edit']"
>修改</el-button>
<el-button
size="mini"
v-if="scope.row.userId !== 1"
type="text"
icon="Delete"
@click="handleDelete(scope.row)"
v-hasPermi="['system:user:remove']"
>删除</el-button>
<el-dropdown v-if="scope.row.userId !== 1" @command="(command) => handleCommand(command, scope.row)">
<span class="el-dropdown-link" v-hasPermi="['system:user:resetPwd', 'system:user:edit']">
<el-icon><d-arrow-right /></el-icon>更多
</span>
<template #dropdown>
<el-dropdown-menu>
<el-dropdown-item command="handleResetPwd" icon="Key"
v-hasPermi="['system:user:resetPwd']">重置密码</el-dropdown-item>
<el-dropdown-item command="handleAuthRole" icon="CircleCheck"
v-hasPermi="['system:user:edit']">分配角色</el-dropdown-item>
</el-dropdown-menu>
</template>
</el-dropdown>
<el-tooltip content="修改" placement="top" v-if="scope.row.userId !== 1">
<el-button
type="text"
icon="Edit"
@click="handleUpdate(scope.row)"
v-hasPermi="['system:user:edit']"
></el-button>
</el-tooltip>
<el-tooltip content="删除" placement="top" v-if="scope.row.userId !== 1">
<el-button
type="text"
icon="Delete"
@click="handleDelete(scope.row)"
v-hasPermi="['system:user:remove']"
></el-button>
</el-tooltip>
<el-tooltip content="重置密码" placement="top" v-if="scope.row.userId !== 1">
<el-button
type="text"
icon="Key"
@click="handleResetPwd(scope.row)"
v-hasPermi="['system:user:resetPwd']"
></el-button>
</el-tooltip>
<el-tooltip content="分配角色" placement="top" v-if="scope.row.userId !== 1">
<el-button
type="text"
icon="CircleCheck"
@click="handleAuthRole(scope.row)"
v-hasPermi="['system:user:edit']"
></el-button>
</el-tooltip>
</template>
</el-table-column>
</el-table>
@@ -417,7 +409,7 @@ const data = reactive({
userName: [{ required: true, message: "用户名称不能为空", trigger: "blur" }, { min: 2, max: 20, message: "用户名称长度必须介于 2 和 20 之间", trigger: "blur" }],
nickName: [{ required: true, message: "用户昵称不能为空", trigger: "blur" }],
password: [{ required: true, message: "用户密码不能为空", trigger: "blur" }, { min: 5, max: 20, message: "用户密码长度必须介于 5 和 20 之间", trigger: "blur" }],
email: [{ type: "email", message: "'请输入正确的邮箱地址", trigger: ["blur", "change"] }],
email: [{ type: "email", message: "请输入正确的邮箱地址", trigger: ["blur", "change"] }],
phonenumber: [{ pattern: /^1[3|4|5|6|7|8|9][0-9]\d{8}$/, message: "请输入正确的手机号码", trigger: "blur" }]
}
});
@@ -451,7 +443,7 @@ function getList() {
/** 节点单击事件 */
function handleNodeClick(data) {
queryParams.value.deptId = data.id;
getList();
handleQuery();
};
/** 搜索按钮操作 */
function handleQuery() {
@@ -548,7 +540,7 @@ const handleFileSuccess = (response, file, fileList) => {
upload.open = false;
upload.isUploading = false;
proxy.$refs["uploadRef"].clearFiles();
proxy.$alert(response.msg, "导入结果", { dangerouslyUseHTMLString: true });
proxy.$alert("<div style='overflow: auto;overflow-x: hidden;max-height: 70vh;padding: 10px 20px 0;'>" + response.msg + "</div>", "导入结果", { dangerouslyUseHTMLString: true });
getList();
};
/** 提交上传文件 */

View File

@@ -10,8 +10,8 @@
<el-input v-model="user.confirmPassword" placeholder="请确认密码" type="password" show-password/>
</el-form-item>
<el-form-item>
<el-button type="primary" size="mini" @click="submit">保存</el-button>
<el-button type="danger" size="mini" @click="close">关闭</el-button>
<el-button type="primary" @click="submit">保存</el-button>
<el-button type="danger" @click="close">关闭</el-button>
</el-form-item>
</el-form>
</template>

View File

@@ -25,26 +25,26 @@
<el-row>
<el-col :lg="2" :md="2">
<el-upload action="#" :http-request="requestUpload" :show-file-list="false" :before-upload="beforeUpload">
<el-button size="small">
<el-button>
选择
<el-icon class="el-icon--right"><Upload /></el-icon>
</el-button>
</el-upload>
</el-col>
<el-col :lg="{span: 1, offset: 2}" :md="2">
<el-button icon="Plus" size="small" @click="changeScale(1)"></el-button>
<el-button icon="Plus" @click="changeScale(1)"></el-button>
</el-col>
<el-col :lg="{span: 1, offset: 1}" :md="2">
<el-button icon="Minus" size="small" @click="changeScale(-1)"></el-button>
<el-button icon="Minus" @click="changeScale(-1)"></el-button>
</el-col>
<el-col :lg="{span: 1, offset: 1}" :md="2">
<el-button icon="RefreshLeft" size="small" @click="rotateLeft()"></el-button>
<el-button icon="RefreshLeft" @click="rotateLeft()"></el-button>
</el-col>
<el-col :lg="{span: 1, offset: 1}" :md="2">
<el-button icon="RefreshRight" size="small" @click="rotateRight()"></el-button>
<el-button icon="RefreshRight" @click="rotateRight()"></el-button>
</el-col>
<el-col :lg="{span: 2, offset: 6}" :md="2">
<el-button type="primary" size="small" @click="uploadImg()"> </el-button>
<el-button type="primary" @click="uploadImg()"> </el-button>
</el-col>
</el-row>
</el-dialog>

View File

@@ -16,8 +16,8 @@
</el-radio-group>
</el-form-item>
<el-form-item>
<el-button type="primary" size="mini" @click="submit">保存</el-button>
<el-button type="danger" size="mini" @click="close">关闭</el-button>
<el-button type="primary" @click="submit">保存</el-button>
<el-button type="danger" @click="close">关闭</el-button>
</el-form-item>
</el-form>
</template>
@@ -35,7 +35,7 @@ const { proxy } = getCurrentInstance();
const rules = ref({
nickName: [{ required: true, message: "用户昵称不能为空", trigger: "blur" }],
email: [{ required: true, message: "邮箱地址不能为空", trigger: "blur" }, { type: "email", message: "'请输入正确的邮箱地址", trigger: ["blur", "change"] }],
email: [{ required: true, message: "邮箱地址不能为空", trigger: "blur" }, { type: "email", message: "请输入正确的邮箱地址", trigger: ["blur", "change"] }],
phonenumber: [{ required: true, message: "手机号码不能为空", trigger: "blur" }, { pattern: /^1[3|4|5|6|7|8|9][0-9]\d{8}$/, message: "请输入正确的手机号码", trigger: "blur" }],
});

View File

@@ -33,6 +33,7 @@
<el-option label="Double" value="Double" />
<el-option label="BigDecimal" value="BigDecimal" />
<el-option label="Date" value="Date" />
<el-option label="Boolean" value="Boolean" />
</el-select>
</template>
</el-table-column>
@@ -117,10 +118,10 @@
</el-tab-pane>
</el-tabs>
<el-form label-width="100px">
<el-form-item style="text-align: center;margin-left:-100px;margin-top:10px;">
<div style="text-align: center;margin-left:-100px;margin-top:10px;">
<el-button type="primary" @click="submitForm()">提交</el-button>
<el-button @click="close()">返回</el-button>
</el-form-item>
</div>
</el-form>
</el-card>
</template>
@@ -180,7 +181,7 @@ function close() {
}
(() => {
const tableId = route.query && route.query.tableId;
const tableId = route.params && route.params.tableId;
if (tableId) {
// 获取表详细信息
getGenTable(tableId).then(res => {

View File

@@ -7,7 +7,6 @@
v-model="queryParams.tableName"
placeholder="请输入表名称"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
@@ -16,13 +15,12 @@
v-model="queryParams.tableComment"
placeholder="请输入表描述"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
<el-row>

View File

@@ -6,7 +6,6 @@
v-model="queryParams.tableName"
placeholder="请输入表名称"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
@@ -15,15 +14,12 @@
v-model="queryParams.tableComment"
placeholder="请输入表描述"
clearable
size="small"
@keyup.enter="handleQuery"
/>
</el-form-item>
<el-form-item label="创建时间">
<el-form-item label="创建时间" style="width: 308px">
<el-date-picker
v-model="dateRange"
size="small"
style="width: 240px"
value-format="YYYY-MM-DD"
type="daterange"
range-separator="-"
@@ -32,8 +28,8 @@
></el-date-picker>
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" size="mini" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" size="mini" @click="resetQuery">重置</el-button>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
@@ -43,7 +39,6 @@
type="primary"
plain
icon="Download"
size="mini"
@click="handleGenTable"
v-hasPermi="['tool:gen:code']"
>生成</el-button>
@@ -53,7 +48,6 @@
type="info"
plain
icon="Upload"
size="mini"
@click="openImportTable"
v-hasPermi="['tool:gen:import']"
>导入</el-button>
@@ -63,7 +57,6 @@
type="success"
plain
icon="Edit"
size="mini"
:disabled="single"
@click="handleEditTable"
v-hasPermi="['tool:gen:edit']"
@@ -74,7 +67,6 @@
type="danger"
plain
icon="Delete"
size="mini"
:disabled="multiple"
@click="handleDelete"
v-hasPermi="['tool:gen:remove']"
@@ -108,45 +100,50 @@
prop="className"
:show-overflow-tooltip="true"
/>
<el-table-column label="创建时间" align="center" prop="createTime" width="150" />
<el-table-column label="更新时间" align="center" prop="updateTime" width="150" />
<el-table-column label="创建时间" align="center" prop="createTime" width="160" />
<el-table-column label="更新时间" align="center" prop="updateTime" width="160" />
<el-table-column label="操作" align="center" width="330" class-name="small-padding fixed-width">
<template #default="scope">
<el-button
type="text"
size="small"
icon="View"
@click="handlePreview(scope.row)"
v-hasPermi="['tool:gen:preview']"
>预览</el-button>
<el-button
type="text"
size="small"
icon="Edit"
@click="handleEditTable(scope.row)"
v-hasPermi="['tool:gen:edit']"
>编辑</el-button>
<el-button
type="text"
size="small"
icon="Delete"
@click="handleDelete(scope.row)"
v-hasPermi="['tool:gen:remove']"
>删除</el-button>
<el-button
type="text"
size="small"
icon="Refresh"
@click="handleSynchDb(scope.row)"
v-hasPermi="['tool:gen:edit']"
>同步</el-button>
<el-button
type="text"
size="small"
icon="Download"
@click="handleGenTable(scope.row)"
v-hasPermi="['tool:gen:code']"
>生成代码</el-button>
<el-tooltip content="预览" placement="top">
<el-button
type="text"
icon="View"
@click="handlePreview(scope.row)"
v-hasPermi="['tool:gen:preview']"
></el-button>
</el-tooltip>
<el-tooltip content="编辑" placement="top">
<el-button
type="text"
icon="Edit"
@click="handleEditTable(scope.row)"
v-hasPermi="['tool:gen:edit']"
></el-button>
</el-tooltip>
<el-tooltip content="删除" placement="top">
<el-button
type="text"
icon="Delete"
@click="handleDelete(scope.row)"
v-hasPermi="['tool:gen:remove']"
></el-button>
</el-tooltip>
<el-tooltip content="同步" placement="top">
<el-button
type="text"
icon="Refresh"
@click="handleSynchDb(scope.row)"
v-hasPermi="['tool:gen:edit']"
></el-button>
</el-tooltip>
<el-tooltip content="生成代码" placement="top">
<el-button
type="text"
icon="Download"
@click="handleGenTable(scope.row)"
v-hasPermi="['tool:gen:code']"
></el-button>
</el-tooltip>
</template>
</el-table-column>
</el-table>
@@ -158,7 +155,7 @@
@pagination="getList"
/>
<!-- 预览界面 -->
<el-dialog :title="preview.title" v-model="preview.open" width="80%" top="5vh" append-to-body class="scrollbar">
<el-dialog :title="preview.title" v-model="preview.open" width="80%" top="5vh" append-to-body custom-class="scrollbar">
<el-tabs v-model="preview.activeName">
<el-tab-pane
v-for="(value, key) in preview.data"
@@ -166,7 +163,7 @@
:name="key.substring(key.lastIndexOf('/')+1,key.indexOf('.vm'))"
:key="key"
>
<pre><code class="hljs" v-html="value"></code></pre>
<pre>{{ value }}</pre>
</el-tab-pane>
</el-tabs>
</el-dialog>
@@ -191,6 +188,7 @@ const multiple = ref(true);
const total = ref(0);
const tableNames = ref([]);
const dateRange = ref([]);
const uniqueId = ref("");
const data = reactive({
queryParams: {
@@ -209,6 +207,17 @@ const data = reactive({
const { queryParams, preview } = toRefs(data);
onActivated(() => {
const time = route.query.t;
if (time != null && time != uniqueId.value) {
uniqueId.value = time;
queryParams.value.pageNum = Number(route.query.pageNum);
dateRange.value = [];
proxy.resetForm("queryForm");
getList();
}
})
/** 查询表集合 */
function getList() {
loading.value = true;
@@ -275,7 +284,7 @@ function handleSelectionChange(selection) {
/** 修改按钮操作 */
function handleEditTable(row) {
const tableId = row.tableId || ids.value[0];
router.push({ path: "/tool/gen-edit/index", query: { tableId: tableId, pageNum: queryParams.value.pageNum } });
router.push({ path: "/tool/gen-edit/index/" + tableId, query: { pageNum: queryParams.value.pageNum } });
}
/** 删除按钮操作 */
function handleDelete(row) {

View File

@@ -5,7 +5,12 @@ import createVitePlugins from './vite/plugins'
// https://vitejs.dev/config/
export default defineConfig(({ mode, command }) => {
const env = loadEnv(mode, process.cwd())
const { VITE_APP_ENV } = env
return {
// 部署生产环境和开发环境下的URL。
// 默认情况下vite 会假设你的应用是被部署在一个域名的根路径上
// 例如 https://www.ruoyi.vip/。如果应用被部署在一个子路径上,你就需要用这个选项指定这个子路径。例如,如果你的应用被部署在 https://www.ruoyi.vip/admin/,则设置 baseUrl 为 /admin/。
base: VITE_APP_ENV === 'production' ? '/' : '/',
plugins: createVitePlugins(env, command === 'build'),
resolve: {
// https://cn.vitejs.dev/config/#resolve-alias
@@ -18,9 +23,10 @@ export default defineConfig(({ mode, command }) => {
// https://cn.vitejs.dev/config/#resolve-extensions
extensions: ['.mjs', '.js', '.ts', '.jsx', '.tsx', '.json', '.vue']
},
// vite 相关配置
// vite 相关配置
server: {
port: 80,
host: true,
open: true,
proxy: {
// https://cn.vitejs.dev/config/#server-proxy
@@ -29,7 +35,24 @@ export default defineConfig(({ mode, command }) => {
changeOrigin: true,
rewrite: (p) => p.replace(/^\/dev-api/, '')
}
},
}
},
//fix:error:stdin>:7356:1: warning: "@charset" must be the first rule in the file
css: {
postcss: {
plugins: [
{
postcssPlugin: 'internal:charset-removal',
AtRule: {
charset: (atRule) => {
if (atRule.name === 'charset') {
atRule.remove();
}
}
}
}
]
}
}
}
})

View File

@@ -2,24 +2,27 @@ import compression from 'vite-plugin-compression'
export default function createCompression(env) {
const { VITE_BUILD_COMPRESS } = env
const compressList = VITE_BUILD_COMPRESS.split(',')
const plugin = []
if (compressList.includes('gzip')) {
plugin.push(
compression({
ext: '.gz',
deleteOriginFile: false
})
)
}
if (compressList.includes('brotli')) {
plugin.push(
compression({
ext: '.br',
algorithm: 'brotliCompress',
deleteOriginFile: false
})
)
if (VITE_BUILD_COMPRESS) {
const compressList = VITE_BUILD_COMPRESS.split(',')
if (compressList.includes('gzip')) {
// http://doc.ruoyi.vip/ruoyi-vue/other/faq.html#使用gzip解压缩静态文件
plugin.push(
compression({
ext: '.gz',
deleteOriginFile: false
})
)
}
if (compressList.includes('brotli')) {
plugin.push(
compression({
ext: '.br',
algorithm: 'brotliCompress',
deleteOriginFile: false
})
)
}
}
return plugin
}