Commit 4765f9b9f2b70ba60b847e819dc5686e3bf23ed7
Merge remote-tracking branch 'origin/wvp-28181-2.0' into wvp-28181-2.0
Showing
10 changed files
with
617 additions
and
2 deletions
src/main/java/com/genersoft/iot/vmp/service/IUserService.java
| 1 | package com.genersoft.iot.vmp.service; | 1 | package com.genersoft.iot.vmp.service; |
| 2 | 2 | ||
| 3 | import com.genersoft.iot.vmp.storager.dao.dto.User; | 3 | import com.genersoft.iot.vmp.storager.dao.dto.User; |
| 4 | +import com.github.pagehelper.PageInfo; | ||
| 4 | 5 | ||
| 5 | import java.util.List; | 6 | import java.util.List; |
| 6 | 7 | ||
| @@ -21,4 +22,8 @@ public interface IUserService { | @@ -21,4 +22,8 @@ public interface IUserService { | ||
| 21 | int updateUsers(User user); | 22 | int updateUsers(User user); |
| 22 | 23 | ||
| 23 | boolean checkPushAuthority(String callId, String sign); | 24 | boolean checkPushAuthority(String callId, String sign); |
| 25 | + | ||
| 26 | + PageInfo<User> getUsers(int page, int count); | ||
| 27 | + | ||
| 28 | + int resetPushKey(int id); | ||
| 24 | } | 29 | } |
src/main/java/com/genersoft/iot/vmp/service/impl/UserServiceImpl.java
| @@ -3,6 +3,8 @@ package com.genersoft.iot.vmp.service.impl; | @@ -3,6 +3,8 @@ package com.genersoft.iot.vmp.service.impl; | ||
| 3 | import com.genersoft.iot.vmp.service.IUserService; | 3 | import com.genersoft.iot.vmp.service.IUserService; |
| 4 | import com.genersoft.iot.vmp.storager.dao.UserMapper; | 4 | import com.genersoft.iot.vmp.storager.dao.UserMapper; |
| 5 | import com.genersoft.iot.vmp.storager.dao.dto.User; | 5 | import com.genersoft.iot.vmp.storager.dao.dto.User; |
| 6 | +import com.github.pagehelper.PageHelper; | ||
| 7 | +import com.github.pagehelper.PageInfo; | ||
| 6 | import org.springframework.beans.factory.annotation.Autowired; | 8 | import org.springframework.beans.factory.annotation.Autowired; |
| 7 | import org.springframework.stereotype.Service; | 9 | import org.springframework.stereotype.Service; |
| 8 | import org.springframework.util.StringUtils; | 10 | import org.springframework.util.StringUtils; |
| @@ -11,7 +13,7 @@ import java.util.List; | @@ -11,7 +13,7 @@ import java.util.List; | ||
| 11 | 13 | ||
| 12 | @Service | 14 | @Service |
| 13 | public class UserServiceImpl implements IUserService { | 15 | public class UserServiceImpl implements IUserService { |
| 14 | - | 16 | + |
| 15 | @Autowired | 17 | @Autowired |
| 16 | private UserMapper userMapper; | 18 | private UserMapper userMapper; |
| 17 | 19 | ||
| @@ -64,4 +66,16 @@ public class UserServiceImpl implements IUserService { | @@ -64,4 +66,16 @@ public class UserServiceImpl implements IUserService { | ||
| 64 | return userMapper.checkPushAuthorityByCallIdAndSign(callId, sign).size() > 0; | 66 | return userMapper.checkPushAuthorityByCallIdAndSign(callId, sign).size() > 0; |
| 65 | } | 67 | } |
| 66 | } | 68 | } |
| 69 | + | ||
| 70 | + @Override | ||
| 71 | + public PageInfo<User> getUsers(int page, int count) { | ||
| 72 | + PageHelper.startPage(page, count); | ||
| 73 | + List<User> users = userMapper.getUsers(); | ||
| 74 | + return new PageInfo<>(users); | ||
| 75 | + } | ||
| 76 | + | ||
| 77 | + @Override | ||
| 78 | + public int resetPushKey(int id) { | ||
| 79 | + return userMapper.resetPushKey(id); | ||
| 80 | + } | ||
| 67 | } | 81 | } |
src/main/java/com/genersoft/iot/vmp/storager/dao/UserMapper.java
| @@ -55,4 +55,11 @@ public interface UserMapper { | @@ -55,4 +55,11 @@ public interface UserMapper { | ||
| 55 | 55 | ||
| 56 | @Select("select * from user where md5(pushKey) = '${sign}'") | 56 | @Select("select * from user where md5(pushKey) = '${sign}'") |
| 57 | List<User> checkPushAuthorityByCallId(String sign); | 57 | List<User> checkPushAuthorityByCallId(String sign); |
| 58 | + | ||
| 59 | + @Select("select u.idu.username,u.pushKey,u.roleId, r.id as roleID, r.name as roleName, r.authority as roleAuthority , r.createTime as roleCreateTime , r.updateTime as roleUpdateTime FROM user u join user_role r on u.roleId=r.id") | ||
| 60 | + @ResultMap(value="roleMap") | ||
| 61 | + List<User> getUsers(); | ||
| 62 | + | ||
| 63 | + @Delete("update user set pushKey=MD5(NOW()+#{id}) where id=#{id}") | ||
| 64 | + int resetPushKey(int id); | ||
| 58 | } | 65 | } |
src/main/java/com/genersoft/iot/vmp/vmanager/user/UserController.java
| @@ -8,6 +8,7 @@ import com.genersoft.iot.vmp.storager.dao.dto.Role; | @@ -8,6 +8,7 @@ import com.genersoft.iot.vmp.storager.dao.dto.Role; | ||
| 8 | import com.genersoft.iot.vmp.storager.dao.dto.User; | 8 | import com.genersoft.iot.vmp.storager.dao.dto.User; |
| 9 | import com.genersoft.iot.vmp.utils.DateUtil; | 9 | import com.genersoft.iot.vmp.utils.DateUtil; |
| 10 | import com.genersoft.iot.vmp.vmanager.bean.WVPResult; | 10 | import com.genersoft.iot.vmp.vmanager.bean.WVPResult; |
| 11 | +import com.github.pagehelper.PageInfo; | ||
| 11 | import io.swagger.annotations.Api; | 12 | import io.swagger.annotations.Api; |
| 12 | import io.swagger.annotations.ApiImplicitParam; | 13 | import io.swagger.annotations.ApiImplicitParam; |
| 13 | import io.swagger.annotations.ApiImplicitParams; | 14 | import io.swagger.annotations.ApiImplicitParams; |
| @@ -177,4 +178,67 @@ public class UserController { | @@ -177,4 +178,67 @@ public class UserController { | ||
| 177 | result.setData(allUsers); | 178 | result.setData(allUsers); |
| 178 | return new ResponseEntity<>(result, HttpStatus.OK); | 179 | return new ResponseEntity<>(result, HttpStatus.OK); |
| 179 | } | 180 | } |
| 181 | + | ||
| 182 | + /** | ||
| 183 | + * 分页查询用户 | ||
| 184 | + * | ||
| 185 | + * @param page 当前页 | ||
| 186 | + * @param count 每页查询数量 | ||
| 187 | + * @return 分页用户列表 | ||
| 188 | + */ | ||
| 189 | + @ApiOperation("分页查询用户") | ||
| 190 | + @ApiImplicitParams({ | ||
| 191 | + @ApiImplicitParam(name = "page", value = "当前页", required = true, dataTypeClass = Integer.class), | ||
| 192 | + @ApiImplicitParam(name = "count", value = "每页查询数量", required = true, dataTypeClass = Integer.class), | ||
| 193 | + }) | ||
| 194 | + @GetMapping("/users") | ||
| 195 | + public PageInfo<User> users(int page, int count) { | ||
| 196 | + return userService.getUsers(page, count); | ||
| 197 | + } | ||
| 198 | + | ||
| 199 | + @ApiOperation("重置pushkey") | ||
| 200 | + @ApiImplicitParams({ | ||
| 201 | + @ApiImplicitParam(name = "id", required = true, value = "用户Id", dataTypeClass = Integer.class), | ||
| 202 | + }) | ||
| 203 | + @RequestMapping("/resetPushKey") | ||
| 204 | + public ResponseEntity<WVPResult<String>> resetPushKey(@RequestParam Integer id) { | ||
| 205 | + // 获取当前登录用户id | ||
| 206 | + int currenRoleId = SecurityUtils.getUserInfo().getRole().getId(); | ||
| 207 | + WVPResult<String> result = new WVPResult<>(); | ||
| 208 | + if (currenRoleId != 1) { | ||
| 209 | + // 只用角色id为0才可以删除和添加用户 | ||
| 210 | + result.setCode(-1); | ||
| 211 | + result.setMsg("用户无权限"); | ||
| 212 | + return new ResponseEntity<>(result, HttpStatus.FORBIDDEN); | ||
| 213 | + } | ||
| 214 | + int resetPushKeyResult = userService.resetPushKey(id); | ||
| 215 | + | ||
| 216 | + result.setCode(resetPushKeyResult > 0 ? 0 : -1); | ||
| 217 | + result.setMsg(resetPushKeyResult > 0 ? "success" : "fail"); | ||
| 218 | + return new ResponseEntity<>(result, HttpStatus.OK); | ||
| 219 | + } | ||
| 220 | + | ||
| 221 | + @ApiOperation("管理员修改普通用户密码") | ||
| 222 | + @ApiImplicitParams({ | ||
| 223 | + @ApiImplicitParam(name = "adminId", required = true, value = "管理员id", dataTypeClass = String.class), | ||
| 224 | + @ApiImplicitParam(name = "userId", required = true, value = "用户id", dataTypeClass = String.class), | ||
| 225 | + @ApiImplicitParam(name = "password", required = true, value = "新密码(未md5加密的密码)", dataTypeClass = String.class), | ||
| 226 | + }) | ||
| 227 | + @PostMapping("/changePasswordForAdmin") | ||
| 228 | + public String changePasswordForAdmin(@RequestParam int userId, @RequestParam String password) { | ||
| 229 | + // 获取当前登录用户id | ||
| 230 | + LoginUser userInfo = SecurityUtils.getUserInfo(); | ||
| 231 | + if (userInfo == null) { | ||
| 232 | + return "fail"; | ||
| 233 | + } | ||
| 234 | + Role role = userInfo.getRole(); | ||
| 235 | + if (role != null && role.getId() == 1) { | ||
| 236 | + boolean result = userService.changePassword(userId, DigestUtils.md5DigestAsHex(password.getBytes())); | ||
| 237 | + if (result) { | ||
| 238 | + return "success"; | ||
| 239 | + } | ||
| 240 | + } | ||
| 241 | + | ||
| 242 | + return "fail"; | ||
| 243 | + } | ||
| 180 | } | 244 | } |
web_src/src/components/Login.vue
| @@ -86,7 +86,7 @@ export default { | @@ -86,7 +86,7 @@ export default { | ||
| 86 | }).then(function (res) { | 86 | }).then(function (res) { |
| 87 | console.log(JSON.stringify(res)); | 87 | console.log(JSON.stringify(res)); |
| 88 | if (res.data.code == 0 && res.data.msg == "success") { | 88 | if (res.data.code == 0 && res.data.msg == "success") { |
| 89 | - that.$cookies.set("session", {"username": that.username}) ; | 89 | + that.$cookies.set("session", {"username": that.username,"roleId":res.data.data.role.id}) ; |
| 90 | //登录成功后 | 90 | //登录成功后 |
| 91 | that.cancelEnterkeyDefaultAction(); | 91 | that.cancelEnterkeyDefaultAction(); |
| 92 | that.$router.push('/'); | 92 | that.$router.push('/'); |
web_src/src/components/UserManager.vue
0 → 100644
| 1 | +<template> | ||
| 2 | + | ||
| 3 | + <div id="app" style="width: 100%"> | ||
| 4 | + <div class="page-header"> | ||
| 5 | + | ||
| 6 | + <div class="page-title">用户列表</div> | ||
| 7 | + <div class="page-header-btn"> | ||
| 8 | + <el-button icon="el-icon-plus" size="mini" style="margin-right: 1rem;" type="primary" @click="addUser"> | ||
| 9 | + 添加用户 | ||
| 10 | + </el-button> | ||
| 11 | + | ||
| 12 | + </div> | ||
| 13 | + </div> | ||
| 14 | + <!--用户列表--> | ||
| 15 | + <el-table :data="userList" style="width: 100%;font-size: 12px;" :height="winHeight" | ||
| 16 | + header-row-class-name="table-header"> | ||
| 17 | + <el-table-column prop="username" label="用户名" min-width="160"/> | ||
| 18 | + <el-table-column prop="pushKey" label="pushkey" min-width="160"/> | ||
| 19 | + <el-table-column prop="role.name" label="类型" min-width="160"/> | ||
| 20 | + <el-table-column label="操作" min-width="450" fixed="right"> | ||
| 21 | + <template slot-scope="scope"> | ||
| 22 | + <el-button size="medium" icon="el-icon-edit" type="text" @click="edit(scope.row)">修改密码</el-button> | ||
| 23 | + <el-divider direction="vertical"></el-divider> | ||
| 24 | + <el-button size="medium" icon="el-icon-refresh" type="text" @click="resetPushKey(scope.row)">重置pushkey</el-button> | ||
| 25 | + <el-divider direction="vertical"></el-divider> | ||
| 26 | + <el-button size="medium" icon="el-icon-delete" type="text" @click="deleteUser(scope.row)" | ||
| 27 | + style="color: #f56c6c">删除 | ||
| 28 | + </el-button> | ||
| 29 | + </template> | ||
| 30 | + </el-table-column> | ||
| 31 | + </el-table> | ||
| 32 | + <changePasswordForAdmin ref="changePasswordForAdmin"></changePasswordForAdmin> | ||
| 33 | + <addUser ref="addUser"></addUser> | ||
| 34 | + <el-pagination | ||
| 35 | + style="float: right" | ||
| 36 | + @size-change="handleSizeChange" | ||
| 37 | + @current-change="currentChange" | ||
| 38 | + :current-page="currentPage" | ||
| 39 | + :page-size="count" | ||
| 40 | + :page-sizes="[15, 25, 35, 50]" | ||
| 41 | + layout="total, sizes, prev, pager, next" | ||
| 42 | + :total="total"> | ||
| 43 | + </el-pagination> | ||
| 44 | + </div> | ||
| 45 | +</template> | ||
| 46 | + | ||
| 47 | +<script> | ||
| 48 | +import uiHeader from '../layout/UiHeader.vue' | ||
| 49 | +import changePasswordForAdmin from './dialog/changePasswordForAdmin.vue' | ||
| 50 | +import addUser from '../components/dialog/addUser.vue' | ||
| 51 | + | ||
| 52 | +export default { | ||
| 53 | + name: 'userManager', | ||
| 54 | + components: { | ||
| 55 | + uiHeader, | ||
| 56 | + changePasswordForAdmin, | ||
| 57 | + addUser | ||
| 58 | + }, | ||
| 59 | + data() { | ||
| 60 | + return { | ||
| 61 | + userList: [], //设备列表 | ||
| 62 | + currentUser: {}, //当前操作设备对象 | ||
| 63 | + | ||
| 64 | + videoComponentList: [], | ||
| 65 | + updateLooper: 0, //数据刷新轮训标志 | ||
| 66 | + currentUserLenth: 0, | ||
| 67 | + winHeight: window.innerHeight - 200, | ||
| 68 | + currentPage: 1, | ||
| 69 | + count: 15, | ||
| 70 | + total: 0, | ||
| 71 | + getUserListLoading: false | ||
| 72 | + }; | ||
| 73 | + }, | ||
| 74 | + mounted() { | ||
| 75 | + this.initData(); | ||
| 76 | + this.updateLooper = setInterval(this.initData, 10000); | ||
| 77 | + }, | ||
| 78 | + destroyed() { | ||
| 79 | + this.$destroy('videojs'); | ||
| 80 | + clearTimeout(this.updateLooper); | ||
| 81 | + }, | ||
| 82 | + methods: { | ||
| 83 | + initData: function () { | ||
| 84 | + this.getUserList(); | ||
| 85 | + }, | ||
| 86 | + currentChange: function (val) { | ||
| 87 | + this.currentPage = val; | ||
| 88 | + this.getUserList(); | ||
| 89 | + }, | ||
| 90 | + handleSizeChange: function (val) { | ||
| 91 | + this.count = val; | ||
| 92 | + this.getUserList(); | ||
| 93 | + }, | ||
| 94 | + getUserList: function () { | ||
| 95 | + let that = this; | ||
| 96 | + this.getUserListLoading = true; | ||
| 97 | + this.$axios({ | ||
| 98 | + method: 'get', | ||
| 99 | + url: `/api/user/users`, | ||
| 100 | + params: { | ||
| 101 | + page: that.currentPage, | ||
| 102 | + count: that.count | ||
| 103 | + } | ||
| 104 | + }).then(function (res) { | ||
| 105 | + that.total = res.data.total; | ||
| 106 | + that.userList = res.data.list; | ||
| 107 | + that.getUserListLoading = false; | ||
| 108 | + }).catch(function (error) { | ||
| 109 | + that.getUserListLoading = false; | ||
| 110 | + }); | ||
| 111 | + | ||
| 112 | + }, | ||
| 113 | + edit: function (row) { | ||
| 114 | + this.$refs.changePasswordForAdmin.openDialog(row, () => { | ||
| 115 | + this.$refs.changePasswordForAdmin.close(); | ||
| 116 | + this.$message({ | ||
| 117 | + showClose: true, | ||
| 118 | + message: "密码修改成功", | ||
| 119 | + type: "success", | ||
| 120 | + }); | ||
| 121 | + setTimeout(this.getDeviceList, 200) | ||
| 122 | + | ||
| 123 | + }) | ||
| 124 | + }, | ||
| 125 | + deleteUser: function (row) { | ||
| 126 | + let msg = "确定删除此用户?" | ||
| 127 | + if (row.online !== 0) { | ||
| 128 | + msg = "<strong>确定删除此用户?</strong>" | ||
| 129 | + } | ||
| 130 | + this.$confirm(msg, '提示', { | ||
| 131 | + dangerouslyUseHTMLString: true, | ||
| 132 | + confirmButtonText: '确定', | ||
| 133 | + cancelButtonText: '取消', | ||
| 134 | + center: true, | ||
| 135 | + type: 'warning' | ||
| 136 | + }).then(() => { | ||
| 137 | + this.$axios({ | ||
| 138 | + method: 'delete', | ||
| 139 | + url: `/api/user/delete?id=${row.id}` | ||
| 140 | + }).then((res) => { | ||
| 141 | + this.getUserList(); | ||
| 142 | + }).catch((error) => { | ||
| 143 | + console.error(error); | ||
| 144 | + }); | ||
| 145 | + }).catch(() => { | ||
| 146 | + | ||
| 147 | + }); | ||
| 148 | + | ||
| 149 | + | ||
| 150 | + }, | ||
| 151 | + resetPushKey: function (row) { | ||
| 152 | + let msg = "确定重置pushkey?" | ||
| 153 | + if (row.online !== 0) { | ||
| 154 | + msg = "<strong>确定重置pushkey?</strong>" | ||
| 155 | + } | ||
| 156 | + this.$confirm(msg, '提示', { | ||
| 157 | + dangerouslyUseHTMLString: true, | ||
| 158 | + confirmButtonText: '确定', | ||
| 159 | + cancelButtonText: '取消', | ||
| 160 | + center: true, | ||
| 161 | + type: 'warning' | ||
| 162 | + }).then(() => { | ||
| 163 | + this.$axios({ | ||
| 164 | + method: 'get', | ||
| 165 | + url: `/api/user/resetPushKey?id=${row.id}` | ||
| 166 | + }).then((res) => { | ||
| 167 | + this.getUserList(); | ||
| 168 | + }).catch((error) => { | ||
| 169 | + console.error(error); | ||
| 170 | + }); | ||
| 171 | + }).catch(() => { | ||
| 172 | + | ||
| 173 | + }); | ||
| 174 | + | ||
| 175 | + | ||
| 176 | + }, | ||
| 177 | + addUser: function () { | ||
| 178 | + this.$refs.addUser.openDialog() | ||
| 179 | + } | ||
| 180 | + } | ||
| 181 | +} | ||
| 182 | +</script> | ||
| 183 | +<style> | ||
| 184 | +.videoList { | ||
| 185 | + display: flex; | ||
| 186 | + flex-wrap: wrap; | ||
| 187 | + align-content: flex-start; | ||
| 188 | +} | ||
| 189 | + | ||
| 190 | +.video-item { | ||
| 191 | + position: relative; | ||
| 192 | + width: 15rem; | ||
| 193 | + height: 10rem; | ||
| 194 | + margin-right: 1rem; | ||
| 195 | + background-color: #000000; | ||
| 196 | +} | ||
| 197 | + | ||
| 198 | +.video-item-img { | ||
| 199 | + position: absolute; | ||
| 200 | + top: 0; | ||
| 201 | + bottom: 0; | ||
| 202 | + left: 0; | ||
| 203 | + right: 0; | ||
| 204 | + margin: auto; | ||
| 205 | + width: 100%; | ||
| 206 | + height: 100%; | ||
| 207 | +} | ||
| 208 | + | ||
| 209 | +.video-item-img:after { | ||
| 210 | + content: ""; | ||
| 211 | + display: inline-block; | ||
| 212 | + position: absolute; | ||
| 213 | + z-index: 2; | ||
| 214 | + top: 0; | ||
| 215 | + bottom: 0; | ||
| 216 | + left: 0; | ||
| 217 | + right: 0; | ||
| 218 | + margin: auto; | ||
| 219 | + width: 3rem; | ||
| 220 | + height: 3rem; | ||
| 221 | + background-image: url("../assets/loading.png"); | ||
| 222 | + background-size: cover; | ||
| 223 | + background-color: #000000; | ||
| 224 | +} | ||
| 225 | + | ||
| 226 | +.video-item-title { | ||
| 227 | + position: absolute; | ||
| 228 | + bottom: 0; | ||
| 229 | + color: #000000; | ||
| 230 | + background-color: #ffffff; | ||
| 231 | + line-height: 1.5rem; | ||
| 232 | + padding: 0.3rem; | ||
| 233 | + width: 14.4rem; | ||
| 234 | +} | ||
| 235 | + | ||
| 236 | +</style> |
web_src/src/components/dialog/addUser.vue
0 → 100644
| 1 | +<template> | ||
| 2 | + <div id="addUser" v-loading="isLoging"> | ||
| 3 | + <el-dialog | ||
| 4 | + title="添加用户" | ||
| 5 | + width="40%" | ||
| 6 | + top="2rem" | ||
| 7 | + :close-on-click-modal="false" | ||
| 8 | + :visible.sync="showDialog" | ||
| 9 | + :destroy-on-close="true" | ||
| 10 | + @close="close()" | ||
| 11 | + > | ||
| 12 | + <div id="shared" style="margin-right: 20px;"> | ||
| 13 | + <el-form ref="passwordForm" :rules="rules" status-icon label-width="80px"> | ||
| 14 | + <el-form-item label="用户名" prop="username"> | ||
| 15 | + <el-input v-model="username" autocomplete="off"></el-input> | ||
| 16 | + </el-form-item> | ||
| 17 | + <el-form-item label="用户类型" prop="roleId"> | ||
| 18 | + <el-select v-model="roleId" placeholder="请选择"> | ||
| 19 | + <el-option | ||
| 20 | + v-for="item in options" | ||
| 21 | + :key="item.id" | ||
| 22 | + :label="item.name" | ||
| 23 | + :value="item.id"> | ||
| 24 | + </el-option> | ||
| 25 | + </el-select> | ||
| 26 | + </el-form-item> | ||
| 27 | + <el-form-item label="密码" prop="password"> | ||
| 28 | + <el-input v-model="password" autocomplete="off"></el-input> | ||
| 29 | + </el-form-item> | ||
| 30 | + <el-form-item label="确认密码" prop="confirmPassword"> | ||
| 31 | + <el-input v-model="confirmPassword" autocomplete="off"></el-input> | ||
| 32 | + </el-form-item> | ||
| 33 | + | ||
| 34 | + <el-form-item> | ||
| 35 | + <div style="float: right;"> | ||
| 36 | + <el-button type="primary" @click="onSubmit">保存</el-button> | ||
| 37 | + <el-button @click="close">取消</el-button> | ||
| 38 | + </div> | ||
| 39 | + </el-form-item> | ||
| 40 | + </el-form> | ||
| 41 | + </div> | ||
| 42 | + </el-dialog> | ||
| 43 | + </div> | ||
| 44 | +</template> | ||
| 45 | + | ||
| 46 | +<script> | ||
| 47 | + | ||
| 48 | +export default { | ||
| 49 | + name: "addUser", | ||
| 50 | + props: {}, | ||
| 51 | + computed: {}, | ||
| 52 | + created() { | ||
| 53 | + this.getAllRole(); | ||
| 54 | + }, | ||
| 55 | + data() { | ||
| 56 | + let validatePass1 = (rule, value, callback) => { | ||
| 57 | + if (value === '') { | ||
| 58 | + callback(new Error('请输入新密码')); | ||
| 59 | + } else { | ||
| 60 | + if (this.confirmPassword !== '') { | ||
| 61 | + this.$refs.passwordForm.validateField('confirmPassword'); | ||
| 62 | + } | ||
| 63 | + callback(); | ||
| 64 | + } | ||
| 65 | + }; | ||
| 66 | + let validatePass2 = (rule, value, callback) => { | ||
| 67 | + if (this.confirmPassword === '') { | ||
| 68 | + callback(new Error('请再次输入密码')); | ||
| 69 | + } else if (this.confirmPassword !== this.password) { | ||
| 70 | + callback(new Error('两次输入密码不一致!')); | ||
| 71 | + } else { | ||
| 72 | + callback(); | ||
| 73 | + } | ||
| 74 | + }; | ||
| 75 | + return { | ||
| 76 | + value:"", | ||
| 77 | + options: [], | ||
| 78 | + loading: false, | ||
| 79 | + username: null, | ||
| 80 | + password: null, | ||
| 81 | + roleId: null, | ||
| 82 | + confirmPassword: null, | ||
| 83 | + listChangeCallback: null, | ||
| 84 | + showDialog: false, | ||
| 85 | + isLoging: false, | ||
| 86 | + rules: { | ||
| 87 | + newPassword: [{required: true, validator: validatePass1, trigger: "blur"}, { | ||
| 88 | + pattern: /^(?=.*[a-zA-Z])(?=.*\d)(?=.*[~!@#$%^&*()_+`\-={}:";'<>?,.\/]).{8,20}$/, | ||
| 89 | + message: "密码长度在8-20位之间,由字母+数字+特殊字符组成", | ||
| 90 | + },], | ||
| 91 | + confirmPassword: [{required: true, validator: validatePass2, trigger: "blur"}], | ||
| 92 | + }, | ||
| 93 | + }; | ||
| 94 | + }, | ||
| 95 | + methods: { | ||
| 96 | + openDialog: function (callback) { | ||
| 97 | + this.listChangeCallback = callback; | ||
| 98 | + this.showDialog = true; | ||
| 99 | + }, | ||
| 100 | + onSubmit: function () { | ||
| 101 | + this.$axios({ | ||
| 102 | + method: 'post', | ||
| 103 | + url: "/api/user/add", | ||
| 104 | + params: { | ||
| 105 | + username: this.username, | ||
| 106 | + password: this.password, | ||
| 107 | + roleId: this.roleId | ||
| 108 | + } | ||
| 109 | + }).then((res) => { | ||
| 110 | + if (res.data.code === 0) { | ||
| 111 | + this.$message({ | ||
| 112 | + showClose: true, | ||
| 113 | + message: '添加成功', | ||
| 114 | + type: 'success', | ||
| 115 | + | ||
| 116 | + }); | ||
| 117 | + this.showDialog = false; | ||
| 118 | + this.listChangeCallback() | ||
| 119 | + | ||
| 120 | + } else { | ||
| 121 | + this.$message({ | ||
| 122 | + showClose: true, | ||
| 123 | + message: res.data.msg, | ||
| 124 | + type: 'error' | ||
| 125 | + }); | ||
| 126 | + } | ||
| 127 | + }).catch((error) => { | ||
| 128 | + console.error(error) | ||
| 129 | + }); | ||
| 130 | + }, | ||
| 131 | + close: function () { | ||
| 132 | + this.showDialog = false; | ||
| 133 | + this.password = null; | ||
| 134 | + this.confirmPassword = null; | ||
| 135 | + this.username = null; | ||
| 136 | + this.roleId = null; | ||
| 137 | + }, | ||
| 138 | + getAllRole:function () { | ||
| 139 | + | ||
| 140 | + this.$axios({ | ||
| 141 | + method: 'get', | ||
| 142 | + url: "/api/role/all" | ||
| 143 | + }).then((res) => { | ||
| 144 | + this.loading = true; | ||
| 145 | + console.info(res) | ||
| 146 | + res.data | ||
| 147 | + console.info(res.data.code) | ||
| 148 | + if (res.data.code === 0) { | ||
| 149 | + console.info(res.data.data) | ||
| 150 | + this.options=res.data.data | ||
| 151 | + | ||
| 152 | + } | ||
| 153 | + }).catch((error) => { | ||
| 154 | + console.error(error) | ||
| 155 | + }); | ||
| 156 | + } | ||
| 157 | + }, | ||
| 158 | +}; | ||
| 159 | +</script> |
web_src/src/components/dialog/changePasswordForAdmin.vue
0 → 100644
| 1 | +<template> | ||
| 2 | + <div id="changePassword" v-loading="isLoging"> | ||
| 3 | + <el-dialog | ||
| 4 | + title="修改密码" | ||
| 5 | + width="40%" | ||
| 6 | + top="2rem" | ||
| 7 | + :close-on-click-modal="false" | ||
| 8 | + :visible.sync="showDialog" | ||
| 9 | + :destroy-on-close="true" | ||
| 10 | + @close="close()" | ||
| 11 | + > | ||
| 12 | + <div id="shared" style="margin-right: 20px;"> | ||
| 13 | + <el-form ref="passwordForm" :rules="rules" status-icon label-width="80px"> | ||
| 14 | + <el-form-item label="新密码" prop="newPassword" > | ||
| 15 | + <el-input v-model="newPassword" autocomplete="off"></el-input> | ||
| 16 | + </el-form-item> | ||
| 17 | + <el-form-item label="确认密码" prop="confirmPassword"> | ||
| 18 | + <el-input v-model="confirmPassword" autocomplete="off"></el-input> | ||
| 19 | + </el-form-item> | ||
| 20 | + | ||
| 21 | + <el-form-item> | ||
| 22 | + <div style="float: right;"> | ||
| 23 | + <el-button type="primary" @click="onSubmit">保存</el-button> | ||
| 24 | + <el-button @click="close">取消</el-button> | ||
| 25 | + </div> | ||
| 26 | + </el-form-item> | ||
| 27 | + </el-form> | ||
| 28 | + </div> | ||
| 29 | + </el-dialog> | ||
| 30 | + </div> | ||
| 31 | +</template> | ||
| 32 | + | ||
| 33 | +<script> | ||
| 34 | +export default { | ||
| 35 | + name: "changePasswordForAdmin", | ||
| 36 | + props: {}, | ||
| 37 | + computed: {}, | ||
| 38 | + created() {}, | ||
| 39 | + data() { | ||
| 40 | + let validatePass1 = (rule, value, callback) => { | ||
| 41 | + if (value === '') { | ||
| 42 | + callback(new Error('请输入新密码')); | ||
| 43 | + } else { | ||
| 44 | + if (this.confirmPassword !== '') { | ||
| 45 | + this.$refs.passwordForm.validateField('confirmPassword'); | ||
| 46 | + } | ||
| 47 | + callback(); | ||
| 48 | + } | ||
| 49 | + }; | ||
| 50 | + let validatePass2 = (rule, value, callback) => { | ||
| 51 | + if (this.confirmPassword === '') { | ||
| 52 | + callback(new Error('请再次输入密码')); | ||
| 53 | + } else if (this.confirmPassword !== this.newPassword) { | ||
| 54 | + callback(new Error('两次输入密码不一致!')); | ||
| 55 | + } else { | ||
| 56 | + callback(); | ||
| 57 | + } | ||
| 58 | + }; | ||
| 59 | + return { | ||
| 60 | + newPassword: null, | ||
| 61 | + confirmPassword: null, | ||
| 62 | + userId: null, | ||
| 63 | + showDialog: false, | ||
| 64 | + isLoging: false, | ||
| 65 | + listChangeCallback: null, | ||
| 66 | + form: {}, | ||
| 67 | + rules: { | ||
| 68 | + newPassword: [{ required: true, validator: validatePass1, trigger: "blur" }, { | ||
| 69 | + pattern: /^(?=.*[a-zA-Z])(?=.*\d)(?=.*[~!@#$%^&*()_+`\-={}:";'<>?,.\/]).{8,20}$/, | ||
| 70 | + message: "密码长度在8-20位之间,由字母+数字+特殊字符组成", | ||
| 71 | + },], | ||
| 72 | + confirmPassword: [{ required: true, validator: validatePass2, trigger: "blur" }], | ||
| 73 | + }, | ||
| 74 | + }; | ||
| 75 | + }, | ||
| 76 | + methods: { | ||
| 77 | + openDialog: function (row, callback) { | ||
| 78 | + console.log(row) | ||
| 79 | + this.showDialog = true; | ||
| 80 | + this.listChangeCallback = callback; | ||
| 81 | + if (row != null) { | ||
| 82 | + this.form = row; | ||
| 83 | + } | ||
| 84 | + }, | ||
| 85 | + onSubmit: function () { | ||
| 86 | + this.$axios({ | ||
| 87 | + method: 'post', | ||
| 88 | + url:"/api/user/changePasswordForAdmin", | ||
| 89 | + params: { | ||
| 90 | + password: this.newPassword, | ||
| 91 | + userId: this.form.id, | ||
| 92 | + } | ||
| 93 | + }).then((res)=> { | ||
| 94 | + if (res.data === "success"){ | ||
| 95 | + this.$message({ | ||
| 96 | + showClose: true, | ||
| 97 | + message: '修改成功', | ||
| 98 | + type: 'success' | ||
| 99 | + }); | ||
| 100 | + this.showDialog = false; | ||
| 101 | + }else { | ||
| 102 | + this.$message({ | ||
| 103 | + showClose: true, | ||
| 104 | + message: '修改密码失败,是否已登录(接口鉴权关闭无法修改密码)', | ||
| 105 | + type: 'error' | ||
| 106 | + }); | ||
| 107 | + } | ||
| 108 | + }).catch((error)=> { | ||
| 109 | + console.error(error) | ||
| 110 | + }); | ||
| 111 | + }, | ||
| 112 | + close: function () { | ||
| 113 | + this.showDialog = false; | ||
| 114 | + this.newPassword = null; | ||
| 115 | + this.confirmPassword = null; | ||
| 116 | + this.userId=null; | ||
| 117 | + this.adminId=null; | ||
| 118 | + }, | ||
| 119 | + }, | ||
| 120 | +}; | ||
| 121 | +</script> |
web_src/src/layout/UiHeader.vue
| @@ -13,6 +13,7 @@ | @@ -13,6 +13,7 @@ | ||
| 13 | <el-menu-item index="/cloudRecord">云端录像</el-menu-item> | 13 | <el-menu-item index="/cloudRecord">云端录像</el-menu-item> |
| 14 | <el-menu-item index="/mediaServerManger">节点管理</el-menu-item> | 14 | <el-menu-item index="/mediaServerManger">节点管理</el-menu-item> |
| 15 | <el-menu-item index="/parentPlatformList/15/1">国标级联</el-menu-item> | 15 | <el-menu-item index="/parentPlatformList/15/1">国标级联</el-menu-item> |
| 16 | + <el-menu-item v-if="editUser" index="/userManager">用户管理</el-menu-item> | ||
| 16 | 17 | ||
| 17 | <!-- <el-submenu index="/setting">--> | 18 | <!-- <el-submenu index="/setting">--> |
| 18 | <!-- <template slot="title">系统设置</template>--> | 19 | <!-- <template slot="title">系统设置</template>--> |
| @@ -47,9 +48,11 @@ export default { | @@ -47,9 +48,11 @@ export default { | ||
| 47 | alarmNotify: false, | 48 | alarmNotify: false, |
| 48 | sseSource: null, | 49 | sseSource: null, |
| 49 | activeIndex: this.$route.path, | 50 | activeIndex: this.$route.path, |
| 51 | + editUser: this.$cookies.get("session").roleId==1 | ||
| 50 | }; | 52 | }; |
| 51 | }, | 53 | }, |
| 52 | created() { | 54 | created() { |
| 55 | + console.log(this.$cookies.get("session")) | ||
| 53 | if (this.$route.path.startsWith("/channelList")) { | 56 | if (this.$route.path.startsWith("/channelList")) { |
| 54 | this.activeIndex = "/deviceList" | 57 | this.activeIndex = "/deviceList" |
| 55 | } | 58 | } |
web_src/src/router/index.js
| @@ -17,6 +17,7 @@ import sip from '../components/setting/Sip.vue' | @@ -17,6 +17,7 @@ import sip from '../components/setting/Sip.vue' | ||
| 17 | import media from '../components/setting/Media.vue' | 17 | import media from '../components/setting/Media.vue' |
| 18 | import live from '../components/live.vue' | 18 | import live from '../components/live.vue' |
| 19 | import deviceTree from '../components/common/DeviceTree.vue' | 19 | import deviceTree from '../components/common/DeviceTree.vue' |
| 20 | +import userManager from '../components/UserManager.vue' | ||
| 20 | 21 | ||
| 21 | import wasmPlayer from '../components/common/jessibuca.vue' | 22 | import wasmPlayer from '../components/common/jessibuca.vue' |
| 22 | import rtcPlayer from '../components/dialog/rtcPlayer.vue' | 23 | import rtcPlayer from '../components/dialog/rtcPlayer.vue' |
| @@ -103,6 +104,11 @@ export default new VueRouter({ | @@ -103,6 +104,11 @@ export default new VueRouter({ | ||
| 103 | name: 'map', | 104 | name: 'map', |
| 104 | component: map, | 105 | component: map, |
| 105 | }, | 106 | }, |
| 107 | + { | ||
| 108 | + path: '/userManager', | ||
| 109 | + name: 'userManager', | ||
| 110 | + component: userManager, | ||
| 111 | + } | ||
| 106 | ] | 112 | ] |
| 107 | }, | 113 | }, |
| 108 | { | 114 | { |