Merge branch 'master' of https://gitee.com/y_project/RuoYi-Vue into dev
Conflicts:
pom.xml
ruoyi-admin/src/main/java/com/ruoyi/web/controller/system/SysProfileController.java
ruoyi-admin/src/main/resources/application.yml
ruoyi-system/src/main/java/com/ruoyi/system/service/impl/SysMenuServiceImpl.java
ruoyi-ui/package.json
ruoyi-ui/src/router/index.js
ruoyi-ui/src/views/monitor/job/index.vue
ruoyi-ui/src/views/system/dict/index.vue
ruoyi-ui/src/views/system/menu/index.vue
ruoyi-ui/src/views/system/role/index.vue
ruoyi-ui/src/views/system/user/index.vue
ruoyi-ui/src/views/system/user/profile/resetPwd.vue
ruoyi-ui/src/views/tool/gen/index.vue
| | |
| | | { |
| | | return AjaxResult.error("修改用户'" + user.getUserName() + "'失败,邮箱账号已存在"); |
| | | } |
| | | LoginUser loginUser = tokenService.getLoginUser(ServletUtils.getRequest()); |
| | | SysUser sysUser = loginUser.getUser(); |
| | | user.setUserId(sysUser.getUserId()); |
| | | user.setPassword(null); |
| | | if (userService.updateUserProfile(user) > 0) |
| | | { |
| | | LoginUser loginUser = tokenService.getLoginUser(ServletUtils.getRequest()); |
| | | // 更新缓存用户信息 |
| | | loginUser.getUser().setNickName(user.getNickName()); |
| | | loginUser.getUser().setPhonenumber(user.getPhonenumber()); |
| | |
| | | childrenList.add(children); |
| | | router.setChildren(childrenList); |
| | | } else if (menu.getParentId().intValue() == 0 && isInnerLink(menu)) { |
| | | router.setMeta(null); |
| | | router.setMeta(new MetaVo(menu.getMenuName(), menu.getIcon())); |
| | | router.setPath("/inner"); |
| | | List<RouterVo> childrenList = new ArrayList<RouterVo>(); |
| | | RouterVo children = new RouterVo(); |
| | |
| | | "clipboard": "2.0.6", |
| | | "core-js": "3.8.1", |
| | | "echarts": "4.9.0", |
| | | "element-ui": "2.15.2", |
| | | "element-ui": "2.15.3", |
| | | "file-saver": "2.0.4", |
| | | "fuse.js": "6.4.3", |
| | | "highlight.js": "9.18.5", |
| | |
| | | <div> |
| | | <el-upload |
| | | :action="uploadUrl" |
| | | :before-upload="handleBeforeUpload" |
| | | :on-success="handleUploadSuccess" |
| | | :on-error="handleUploadError" |
| | | name="file" |
| | |
| | | readOnly: { |
| | | type: Boolean, |
| | | default: false, |
| | | }, |
| | | // 上传文件大小限制(MB) |
| | | fileSize: { |
| | | type: Number, |
| | | default: 5, |
| | | }, |
| | | /* 类型(base64格式、url格式) */ |
| | | type: { |
| | |
| | | this.quill.format("image", false); |
| | | } |
| | | }); |
| | | // toolbar.addHandler("video", (value) => { |
| | | // this.uploadType = "video"; |
| | | // if (value) { |
| | | // this.$refs.upload.$children[0].$refs.input.click(); |
| | | // } else { |
| | | // this.quill.format("video", false); |
| | | // } |
| | | // }); |
| | | } |
| | | this.Quill.pasteHTML(this.currentValue); |
| | | this.Quill.on("text-change", (delta, oldDelta, source) => { |
| | |
| | | this.$emit("on-editor-change", eventName, ...args); |
| | | }); |
| | | }, |
| | | // 上传前校检格式和大小 |
| | | handleBeforeUpload(file) { |
| | | // 校检文件大小 |
| | | if (this.fileSize) { |
| | | const isLt = file.size / 1024 / 1024 < this.fileSize; |
| | | if (!isLt) { |
| | | this.$message.error(`上传文件大小不能超过 ${this.fileSize} MB!`); |
| | | return false; |
| | | } |
| | | } |
| | | return true; |
| | | }, |
| | | handleUploadSuccess(res, file) { |
| | | // 获取富文本组件实例 |
| | | let quill = this.Quill; |
| | |
| | | </template> |
| | | |
| | | <!-- 顶部菜单超出数量折叠 --> |
| | | <el-submenu index="more" v-if="topMenus.length > visibleNumber"> |
| | | <el-submenu :style="{'--theme': theme}" index="more" v-if="topMenus.length > visibleNumber"> |
| | | <template slot="title">更多菜单</template> |
| | | <template v-for="(item, index) in topMenus"> |
| | | <el-menu-item |
| | |
| | | </script> |
| | | |
| | | <style lang="scss"> |
| | | .el-menu--horizontal > .el-menu-item { |
| | | .topmenu-container.el-menu--horizontal > .el-menu-item { |
| | | float: left; |
| | | height: 50px; |
| | | line-height: 50px; |
| | | margin: 0; |
| | | border-bottom: 3px solid transparent; |
| | | color: #999093; |
| | | padding: 0 5px; |
| | | margin: 0 10px; |
| | | height: 50px !important; |
| | | line-height: 50px !important; |
| | | color: #999093 !important; |
| | | padding: 0 5px !important; |
| | | margin: 0 10px !important; |
| | | } |
| | | |
| | | .el-menu--horizontal > .el-menu-item.is-active { |
| | | border-bottom: 3px solid #{'var(--theme)'}; |
| | | .topmenu-container.el-menu--horizontal > .el-menu-item.is-active, .el-menu--horizontal > .el-submenu.is-active .el-submenu__title { |
| | | border-bottom: 2px solid #{'var(--theme)'} !important; |
| | | color: #303133; |
| | | } |
| | | |
| | | /* submenu item */ |
| | | .el-menu--horizontal > .el-submenu .el-submenu__title { |
| | | height: 50px !important; |
| | | line-height: 50px !important; |
| | | .topmenu-container.el-menu--horizontal > .el-submenu .el-submenu__title { |
| | | float: left; |
| | | height: 50px !important; |
| | | line-height: 50px !important; |
| | | color: #999093 !important; |
| | | padding: 0 5px !important; |
| | | margin: 0 10px !important; |
| | | } |
| | | </style> |
| | |
| | | title: 'title' // 设置该路由在侧边栏和面包屑中展示的名字 |
| | | icon: 'svg-name' // 设置该路由的图标,对应路径src/assets/icons/svg |
| | | breadcrumb: false // 如果设置为false,则不会在breadcrumb面包屑中显示 |
| | | activeMenu: '/system/user' // 当路由设置了该属性,则会高亮相对应的侧边栏。 |
| | | } |
| | | */ |
| | | |
| | |
| | | ] |
| | | }, |
| | | { |
| | | path: '/auth', |
| | | path: '/system/user-auth', |
| | | component: Layout, |
| | | hidden: true, |
| | | children: [ |
| | |
| | | path: 'role/:userId(\\d+)', |
| | | component: (resolve) => require(['@/views/system/user/authRole'], resolve), |
| | | name: 'AuthRole', |
| | | meta: { title: '分配角色'} |
| | | meta: { title: '分配角色', activeMenu: '/system/user'} |
| | | } |
| | | ] |
| | | }, |
| | | { |
| | | path: '/auth', |
| | | path: '/system/role-auth', |
| | | component: Layout, |
| | | hidden: true, |
| | | children: [ |
| | |
| | | path: 'user/:roleId(\\d+)', |
| | | component: (resolve) => require(['@/views/system/role/authUser'], resolve), |
| | | name: 'AuthUser', |
| | | meta: { title: '分配用户'} |
| | | meta: { title: '分配用户', activeMenu: '/system/role'} |
| | | } |
| | | ] |
| | | }, |
| | | { |
| | | path: '/dict', |
| | | path: '/system/dict-data', |
| | | component: Layout, |
| | | hidden: true, |
| | | children: [ |
| | | { |
| | | path: 'type/data/:dictId(\\d+)', |
| | | path: 'index/:dictId(\\d+)', |
| | | component: (resolve) => require(['@/views/system/dict/data'], resolve), |
| | | name: 'Data', |
| | | meta: { title: '字典数据', icon: '' } |
| | | meta: { title: '字典数据', activeMenu: '/system/dict'} |
| | | } |
| | | ] |
| | | }, |
| | | { |
| | | path: '/job', |
| | | path: '/monitor/job-log', |
| | | component: Layout, |
| | | hidden: true, |
| | | children: [ |
| | | { |
| | | path: 'log', |
| | | path: 'index', |
| | | component: (resolve) => require(['@/views/monitor/job/log'], resolve), |
| | | name: 'JobLog', |
| | | meta: { title: '调度日志' } |
| | | meta: { title: '调度日志', activeMenu: '/monitor/job'} |
| | | } |
| | | ] |
| | | }, |
| | | { |
| | | path: '/gen', |
| | | path: '/tool/gen-edit', |
| | | component: Layout, |
| | | hidden: true, |
| | | children: [ |
| | | { |
| | | path: 'edit/:tableId(\\d+)', |
| | | path: 'index/:tableId(\\d+)', |
| | | component: (resolve) => require(['@/views/tool/gen/editTable'], resolve), |
| | | name: 'GenEdit', |
| | | meta: { title: '修改生成配置' } |
| | | meta: { title: '修改生成配置', activeMenu: '/tool/gen'} |
| | | } |
| | | ] |
| | | } |
| | |
| | | @click="handleDelete(scope.row)" |
| | | v-hasPermi="['monitor:job:remove']" |
| | | >删除</el-button> |
| | | <el-dropdown size="mini" @command="(command) => handleCommand(command, scope.row)"> |
| | | <el-dropdown size="mini" @command="(command) => handleCommand(command, scope.row)" v-hasPermi="['monitor:job:changeStatus', 'monitor:job:query']"> |
| | | <span class="el-dropdown-link"> |
| | | <i class="el-icon-d-arrow-right el-icon--right"></i>更多 |
| | | </span> |
| | |
| | | /** 任务日志列表查询 */ |
| | | handleJobLog(row) { |
| | | const jobId = row.jobId || 0; |
| | | this.$router.push({ path: '/job/log', query: { jobId: jobId } }) |
| | | this.$router.push({ path: '/monitor/job-log/index', query: { jobId: jobId } }) |
| | | }, |
| | | /** 新增按钮操作 */ |
| | | handleAdd() { |
| | |
| | | } else { |
| | | this.getList(); |
| | | } |
| | | this.getDicts("sys_job_status").then(response => { |
| | | this.getDicts("sys_common_status").then(response => { |
| | | this.statusOptions = response.data; |
| | | }); |
| | | this.getDicts("sys_job_group").then(response => { |
| | |
| | | <el-table-column label="字典名称" align="center" prop="dictName" :show-overflow-tooltip="true" /> |
| | | <el-table-column label="字典类型" align="center" :show-overflow-tooltip="true"> |
| | | <template slot-scope="scope"> |
| | | <router-link :to="'/dict/type/data/' + scope.row.dictId" class="link-type"> |
| | | <router-link :to="'/system/dict-data/index/' + scope.row.dictId" class="link-type"> |
| | | <span>{{ scope.row.dictType }}</span> |
| | | </router-link> |
| | | </template> |
| | |
| | | |
| | | <!-- 添加或修改菜单对话框 --> |
| | | <el-dialog :title="title" :visible.sync="open" width="600px" append-to-body> |
| | | <el-form ref="form" :model="form" :rules="rules" label-width="80px"> |
| | | <el-form ref="form" :model="form" :rules="rules" label-width="100px"> |
| | | <el-row> |
| | | <el-col :span="24"> |
| | | <el-form-item label="上级菜单"> |
| | |
| | | </el-form-item> |
| | | </el-col> |
| | | <el-col :span="12"> |
| | | <el-form-item v-if="form.menuType != 'F'" label="是否外链"> |
| | | <el-form-item v-if="form.menuType != 'F'"> |
| | | <span slot="label"> |
| | | <el-tooltip content="选择是外链则路由地址需要以`http(s)://`开头" placement="top"> |
| | | <i class="el-icon-question"></i> |
| | | </el-tooltip> |
| | | 是否外链 |
| | | </span> |
| | | <el-radio-group v-model="form.isFrame"> |
| | | <el-radio label="0">是</el-radio> |
| | | <el-radio label="1">否</el-radio> |
| | |
| | | </el-form-item> |
| | | </el-col> |
| | | <el-col :span="12"> |
| | | <el-form-item v-if="form.menuType != 'F'" label="路由地址" prop="path"> |
| | | <el-form-item v-if="form.menuType != 'F'" prop="path"> |
| | | <span slot="label"> |
| | | <el-tooltip content="访问的路由地址,如:`user`,如外网地址需内链访问则以`http(s)://`开头" placement="top"> |
| | | <i class="el-icon-question"></i> |
| | | </el-tooltip> |
| | | 路由地址 |
| | | </span> |
| | | <el-input v-model="form.path" placeholder="请输入路由地址" /> |
| | | </el-form-item> |
| | | </el-col> |
| | | <el-col :span="12" v-if="form.menuType == 'C'"> |
| | | <el-form-item label="组件路径" prop="component"> |
| | | <el-form-item prop="component"> |
| | | <span slot="label"> |
| | | <el-tooltip content="访问的组件路径,如:`system/user/index`,默认在`views`目录下" placement="top"> |
| | | <i class="el-icon-question"></i> |
| | | </el-tooltip> |
| | | 组件路径 |
| | | </span> |
| | | <el-input v-model="form.component" placeholder="请输入组件路径" /> |
| | | </el-form-item> |
| | | </el-col> |
| | | <el-col :span="12"> |
| | | <el-form-item v-if="form.menuType != 'M'" label="权限标识"> |
| | | <el-form-item v-if="form.menuType != 'M'"> |
| | | <el-input v-model="form.perms" placeholder="请输入权限标识" maxlength="100" /> |
| | | <span slot="label"> |
| | | <el-tooltip content="控制器中定义的权限字符,如:@PreAuthorize(`@ss.hasPermi('system:user:list')`)" placement="top"> |
| | | <i class="el-icon-question"></i> |
| | | </el-tooltip> |
| | | 权限字符 |
| | | </span> |
| | | </el-form-item> |
| | | </el-col> |
| | | <el-col :span="12"> |
| | | <el-form-item v-if="form.menuType != 'F'" label="显示状态"> |
| | | <el-form-item v-if="form.menuType != 'F'"> |
| | | <span slot="label"> |
| | | <el-tooltip content="选择隐藏则路由将不会出现在侧边栏,但仍然可以访问" placement="top"> |
| | | <i class="el-icon-question"></i> |
| | | </el-tooltip> |
| | | 显示状态 |
| | | </span> |
| | | <el-radio-group v-model="form.visible"> |
| | | <el-radio |
| | | v-for="dict in visibleOptions" |
| | |
| | | </el-form-item> |
| | | </el-col> |
| | | <el-col :span="12"> |
| | | <el-form-item v-if="form.menuType != 'F'" label="菜单状态"> |
| | | <el-form-item v-if="form.menuType != 'F'"> |
| | | <span slot="label"> |
| | | <el-tooltip content="选择停用则路由将不会出现在侧边栏,也不能被访问" placement="top"> |
| | | <i class="el-icon-question"></i> |
| | | </el-tooltip> |
| | | 菜单状态 |
| | | </span> |
| | | <el-radio-group v-model="form.status"> |
| | | <el-radio |
| | | v-for="dict in statusOptions" |
| | |
| | | </el-form-item> |
| | | </el-col> |
| | | <el-col :span="12"> |
| | | <el-form-item v-if="form.menuType == 'C'" label="是否缓存"> |
| | | <el-form-item v-if="form.menuType == 'C'"> |
| | | <span slot="label"> |
| | | <el-tooltip content="选择是则会被`keep-alive`缓存,需要匹配组件的`name`和地址保持一致" placement="top"> |
| | | <i class="el-icon-question"></i> |
| | | </el-tooltip> |
| | | 是否缓存 |
| | | </span> |
| | | <el-radio-group v-model="form.isCache"> |
| | | <el-radio label="0">缓存</el-radio> |
| | | <el-radio label="1">不缓存</el-radio> |
| | |
| | | @click="handleDelete(scope.row)" |
| | | v-hasPermi="['system:role:remove']" |
| | | >删除</el-button> |
| | | <el-dropdown size="mini" @command="(command) => handleCommand(command, scope.row)"> |
| | | <el-dropdown size="mini" @command="(command) => handleCommand(command, scope.row)" v-hasPermi="['system:role:edit']"> |
| | | <span class="el-dropdown-link"> |
| | | <i class="el-icon-d-arrow-right el-icon--right"></i>更多 |
| | | </span> |
| | |
| | | |
| | | <!-- 添加或修改角色配置对话框 --> |
| | | <el-dialog :title="title" :visible.sync="open" width="500px" append-to-body> |
| | | <el-form ref="form" :model="form" :rules="rules" label-width="80px"> |
| | | <el-form ref="form" :model="form" :rules="rules" label-width="100px"> |
| | | <el-form-item label="角色名称" prop="roleName"> |
| | | <el-input v-model="form.roleName" placeholder="请输入角色名称" /> |
| | | </el-form-item> |
| | | <el-form-item label="权限字符" prop="roleKey"> |
| | | <el-form-item prop="roleKey"> |
| | | <span slot="label"> |
| | | <el-tooltip content="控制器中定义的权限字符,如:@PreAuthorize(`@ss.hasRole('admin')`)" placement="top"> |
| | | <i class="el-icon-question"></i> |
| | | </el-tooltip> |
| | | 权限字符 |
| | | </span> |
| | | <el-input v-model="form.roleKey" placeholder="请输入权限字符" /> |
| | | </el-form-item> |
| | | <el-form-item label="角色顺序" prop="roleSort"> |
| | |
| | | /** 分配用户操作 */ |
| | | handleAuthUser: function(row) { |
| | | const roleId = row.roleId; |
| | | this.$router.push("/auth/user/" + roleId); |
| | | this.$router.push("/system/role-auth/user/" + roleId); |
| | | }, |
| | | /** 提交按钮 */ |
| | | submitForm: function() { |
| | |
| | | @click="handleDelete(scope.row)" |
| | | v-hasPermi="['system:user:remove']" |
| | | >删除</el-button> |
| | | <el-dropdown size="mini" @command="(command) => handleCommand(command, scope.row)"> |
| | | <el-dropdown size="mini" @command="(command) => handleCommand(command, scope.row)" v-hasPermi="['system:user:resetPwd', 'system:user:edit']"> |
| | | <span class="el-dropdown-link"> |
| | | <i class="el-icon-d-arrow-right el-icon--right"></i>更多 |
| | | </span> |
| | |
| | | </el-col> |
| | | <el-col :span="12"> |
| | | <el-form-item v-if="form.userId == undefined" label="用户密码" prop="password"> |
| | | <el-input v-model="form.password" placeholder="请输入用户密码" type="password" maxlength="20" /> |
| | | <el-input v-model="form.password" placeholder="请输入用户密码" type="password" maxlength="20" show-password/> |
| | | </el-form-item> |
| | | </el-col> |
| | | </el-row> |
| | |
| | | drag |
| | | > |
| | | <i class="el-icon-upload"></i> |
| | | <div class="el-upload__text"> |
| | | 将文件拖到此处,或 |
| | | <em>点击上传</em> |
| | | <div class="el-upload__text">将文件拖到此处,或<em>点击上传</em></div> |
| | | <div class="el-upload__tip text-center" slot="tip"> |
| | | <div class="el-upload__tip" slot="tip"> |
| | | <el-checkbox v-model="upload.updateSupport" /> 是否更新已经存在的用户数据 |
| | | </div> |
| | | <span>仅允许导入xls、xlsx格式文件。</span> |
| | | <el-link type="primary" :underline="false" style="font-size:12px;vertical-align: baseline;" @click="importTemplate">下载模板</el-link> |
| | | </div> |
| | | <div class="el-upload__tip" slot="tip"> |
| | | <el-checkbox v-model="upload.updateSupport" />是否更新已经存在的用户数据 |
| | | <el-link type="info" style="font-size:12px" @click="importTemplate">下载模板</el-link> |
| | | </div> |
| | | <div class="el-upload__tip" style="color:red" slot="tip">提示:仅允许导入“xls”或“xlsx”格式文件!</div> |
| | | </el-upload> |
| | | <div slot="footer" class="dialog-footer"> |
| | | <el-button type="primary" @click="submitFileForm">确 定</el-button> |
| | |
| | | /** 分配角色操作 */ |
| | | handleAuthRole: function(row) { |
| | | const userId = row.userId; |
| | | this.$router.push("/auth/role/" + userId); |
| | | this.$router.push("/system/user-auth/role/" + userId); |
| | | }, |
| | | /** 提交按钮 */ |
| | | submitForm: function() { |
| | |
| | | <template> |
| | | <el-form ref="form" :model="user" :rules="rules" label-width="80px"> |
| | | <el-form-item label="旧密码" prop="oldPassword"> |
| | | <el-input v-model="user.oldPassword" placeholder="请输入旧密码" type="password" /> |
| | | <el-input v-model="user.oldPassword" placeholder="请输入旧密码" type="password" show-password/> |
| | | </el-form-item> |
| | | <el-form-item label="新密码" prop="newPassword"> |
| | | <el-input v-model="user.newPassword" placeholder="请输入新密码" type="password" /> |
| | | <el-input v-model="user.newPassword" placeholder="请输入新密码" type="password" show-password/> |
| | | </el-form-item> |
| | | <el-form-item label="确认密码" prop="confirmPassword"> |
| | | <el-input v-model="user.confirmPassword" placeholder="请确认密码" type="password" /> |
| | | <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> |
| | |
| | | /** 修改按钮操作 */ |
| | | handleEditTable(row) { |
| | | const tableId = row.tableId || this.ids[0]; |
| | | this.$router.push("/gen/edit/" + tableId); |
| | | this.$router.push("/tool/gen-edit/index/" + tableId); |
| | | }, |
| | | /** 删除按钮操作 */ |
| | | handleDelete(row) { |