Files
gin-vue-admin/web/src/view/superAdmin/user/user.vue
2021-09-21 17:40:28 +08:00

277 lines
9.1 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
<template>
<div>
<div class="gva-table-box">
<div class="gva-btn-list">
<el-button size="mini" type="primary" icon="el-icon-plus" @click="addUser">新增用户</el-button>
</div>
<el-table :data="tableData">
<el-table-column align="center" label="头像" min-width="50">
<template #default="scope">
<CustomPic style="margin-top:8px" :pic-src="scope.row.headerImg" />
</template>
</el-table-column>
<el-table-column align="center" label="UUID" min-width="250" prop="uuid" />
<el-table-column align="center" label="用户名" min-width="150" prop="userName" />
<el-table-column align="center" label="昵称" min-width="150" prop="nickName" />
<el-table-column align="center" label="用户角色" min-width="150">
<template #default="scope">
<el-cascader
v-model="scope.row.authorityIds"
:options="authOptions"
:show-all-levels="false"
collapse-tags
:props="{ multiple:true,checkStrictly: true,label:'authorityName',value:'authorityId',disabled:'disabled',emitPath:false}"
:clearable="false"
@visible-change="(flag)=>{changeAuthority(scope.row,flag)}"
@remove-tag="()=>{changeAuthority(scope.row,false)}"
/>
</template>
</el-table-column>
<el-table-column align="center" label="操作" min-width="150">
<template #default="scope">
<el-popover v-model:visible="scope.row.visible" placement="top" width="160">
<p>确定要删除此用户吗</p>
<div style="text-align: right; margin-top: 8px;">
<el-button size="mini" type="text" @click="scope.row.visible = false">取消</el-button>
<el-button type="primary" size="mini" @click="deleteUser(scope.row)">确定</el-button>
</div>
<template #reference>
<el-button type="text" icon="el-icon-delete" size="mini">删除</el-button>
</template>
</el-popover>
</template>
</el-table-column>
</el-table>
<warning-bar title="右上角头像下拉可切换角色" style="margin-top:12px;" />
<div class="gva-pagination">
<el-pagination
:current-page="page"
:page-size="pageSize"
:page-sizes="[10, 30, 50, 100]"
:total="total"
layout="total, sizes, prev, pager, next, jumper"
@current-change="handleCurrentChange"
@size-change="handleSizeChange"
/>
</div>
</div>
<el-dialog v-model="addUserDialog" custom-class="user-dialog" title="新增用户">
<el-form ref="userForm" :rules="rules" :model="userInfo" label-width="80px">
<el-form-item label="用户名" prop="username">
<el-input v-model="userInfo.username" />
</el-form-item>
<el-form-item label="密码" prop="password">
<el-input v-model="userInfo.password" />
</el-form-item>
<el-form-item label="别名" prop="nickName">
<el-input v-model="userInfo.nickName" />
</el-form-item>
<el-form-item label="用户角色" prop="authorityId">
<el-cascader
v-model="userInfo.authorityIds"
style="width:100%"
:options="authOptions"
:show-all-levels="false"
:props="{ multiple:true,checkStrictly: true,label:'authorityName',value:'authorityId',disabled:'disabled',emitPath:false}"
:clearable="false"
/>
</el-form-item>
<el-form-item label="头像" label-width="80px">
<div style="display:inline-block" @click="openHeaderChange">
<img v-if="userInfo.headerImg" class="header-img-box" :src="(userInfo.headerImg && userInfo.headerImg.slice(0, 4) !== 'http')?path+userInfo.headerImg:userInfo.headerImg">
<div v-else class="header-img-box">从媒体库选择</div>
</div>
</el-form-item>
</el-form>
<template #footer>
<div class="dialog-footer">
<el-button size="small" @click="closeAddUserDialog">取 消</el-button>
<el-button size="small" type="primary" @click="enterAddUserDialog">确 定</el-button>
</div>
</template>
</el-dialog>
<ChooseImg ref="chooseImg" :target="userInfo" :target-key="`headerImg`" />
</div>
</template>
<script>
// 获取列表内容封装在mixins内部 getTableData方法 初始化已封装完成
const path = import.meta.env.VITE_BASE_API
import {
getUserList,
setUserAuthorities,
register,
deleteUser
} from '@/api/user'
import { getAuthorityList } from '@/api/authority'
import infoList from '@/mixins/infoList'
import { mapGetters } from 'vuex'
import CustomPic from '@/components/customPic/index.vue'
import ChooseImg from '@/components/chooseImg/index.vue'
import warningBar from '@/components/warningBar/warningBar.vue'
export default {
name: 'Api',
components: { CustomPic, ChooseImg, warningBar },
mixins: [infoList],
data() {
return {
listApi: getUserList,
path: path,
authOptions: [],
addUserDialog: false,
userInfo: {
username: '',
password: '',
nickName: '',
headerImg: '',
authorityId: '',
authorityIds: []
},
rules: {
username: [
{ required: true, message: '请输入用户名', trigger: 'blur' },
{ min: 5, message: '最低5位字符', trigger: 'blur' }
],
password: [
{ required: true, message: '请输入用户密码', trigger: 'blur' },
{ min: 6, message: '最低6位字符', trigger: 'blur' }
],
nickName: [
{ required: true, message: '请输入用户昵称', trigger: 'blur' }
],
authorityId: [
{ required: true, message: '请选择用户角色', trigger: 'blur' }
]
}
}
},
computed: {
...mapGetters('user', ['token'])
},
watch: {
tableData() {
this.setAuthorityIds()
}
},
async created() {
await this.getTableData()
const res = await getAuthorityList({ page: 1, pageSize: 999 })
this.setOptions(res.data.list)
},
methods: {
setAuthorityIds() {
this.tableData && this.tableData.forEach((user) => {
const authorityIds = user.authorities && user.authorities.map(i => {
return i.authorityId
})
user.authorityIds = authorityIds
})
},
openHeaderChange() {
this.$refs.chooseImg.open()
},
setOptions(authData) {
this.authOptions = []
this.setAuthorityOptions(authData, this.authOptions)
},
setAuthorityOptions(AuthorityData, optionsData) {
AuthorityData &&
AuthorityData.map(item => {
if (item.children && item.children.length) {
const option = {
authorityId: item.authorityId,
authorityName: item.authorityName,
children: []
}
this.setAuthorityOptions(item.children, option.children)
optionsData.push(option)
} else {
const option = {
authorityId: item.authorityId,
authorityName: item.authorityName
}
optionsData.push(option)
}
})
},
async deleteUser(row) {
const res = await deleteUser({ id: row.ID })
if (res.code === 0) {
this.$message.success('删除成功')
await this.getTableData()
row.visible = false
}
},
async enterAddUserDialog() {
this.userInfo.authorityId = this.userInfo.authorityIds[0]
this.$refs.userForm.validate(async valid => {
if (valid) {
const res = await register(this.userInfo)
if (res.code === 0) {
this.$message({ type: 'success', message: '创建成功' })
}
await this.getTableData()
this.closeAddUserDialog()
}
})
},
closeAddUserDialog() {
this.$refs.userForm.resetFields()
this.userInfo.headerImg = ''
this.userInfo.authorityIds = []
this.addUserDialog = false
},
addUser() {
this.addUserDialog = true
},
async changeAuthority(row, flag) {
if (flag) {
return
}
this.$nextTick(async() => {
const res = await setUserAuthorities({
ID: row.ID,
authorityIds: row.authorityIds
})
if (res.code === 0) {
this.$message({ type: 'success', message: '角色设置成功' })
}
})
},
}
}
</script>
<style lang="scss">
.user-dialog {
.header-img-box {
width: 200px;
height: 200px;
border: 1px dashed #ccc;
border-radius: 20px;
text-align: center;
line-height: 200px;
cursor: pointer;
}
.avatar-uploader .el-upload:hover {
border-color: #409eff;
}
.avatar-uploader-icon {
border: 1px dashed #d9d9d9 !important;
border-radius: 6px;
font-size: 28px;
color: #8c939d;
width: 178px;
height: 178px;
line-height: 178px;
text-align: center;
}
.avatar {
width: 178px;
height: 178px;
display: block;
}
}
</style>