提交 a4198c6b authored 作者: 龙菲's avatar 龙菲

角色管理

上级 1c06d651
...@@ -88,6 +88,16 @@ export function upadateUser(data) { ...@@ -88,6 +88,16 @@ export function upadateUser(data) {
}) })
} }
// 删除用户
export function deleteUser(data) {
return request({
url: '/sys/user',
method: 'delete',
data
})
}
// 以用户行为统计排序分页查询资源 // 以用户行为统计排序分页查询资源
export function getListByPageSort(data) { export function getListByPageSort(data) {
return request({ return request({
...@@ -106,3 +116,44 @@ export function getBarMap(params) { ...@@ -106,3 +116,44 @@ export function getBarMap(params) {
}) })
} }
// 增加角色
export function addRole(data) {
return request({
url: '/sys/role',
method: 'post',
data
})
}
// 修改角色
export function upadateRole(data) {
return request({
url: 'sys/role',
method: 'put',
data
})
}
// 删除角色
export function deleteRole(id) {
return request({
url: '/sys/role/'+id,
method: 'delete',
})
}
// 获取所有目录菜单树
export function getPermissionTreeAll(params) {
return request({
url: '/sys/permission/tree/all',
method: 'get',
params
})
}
export function getPermissionById(id) {
return request({
url: `/sys/permission/${id}`,
method: 'get',
})
}
import { import {
login, login,
logout, logout,
getMenu getMenu,
getPermissionTreeAll
} from '@/api/user' } from '@/api/user'
import { import {
getToken, getToken,
...@@ -25,6 +26,7 @@ const getDefaultState = () => { ...@@ -25,6 +26,7 @@ const getDefaultState = () => {
menu: getLocalMenu(), menu: getLocalMenu(),
name: '', name: '',
avatar: '', avatar: '',
permissionTree: []
} }
} }
...@@ -48,7 +50,10 @@ const mutations = { ...@@ -48,7 +50,10 @@ const mutations = {
}, },
SET_MENU: (state, menu) => { SET_MENU: (state, menu) => {
state.menu = menu state.menu = menu
} },
SET_PERMISSION_TREE_ALL: (state, permissionTree) => {
state.permissionTree = permissionTree
},
} }
const actions = { const actions = {
...@@ -143,7 +148,7 @@ const actions = { ...@@ -143,7 +148,7 @@ const actions = {
} }
return obj return obj
} }
commit('SET_MENU', menuObj) commit('SET_MENU', menuObj)
setLocalMenu(menuObj) setLocalMenu(menuObj)
resolve() resolve()
...@@ -153,6 +158,19 @@ const actions = { ...@@ -153,6 +158,19 @@ const actions = {
}) })
}, },
// 获取权限树所有
getPermissionTreeAll({
commit
}) {
return new Promise(resolve => {
getPermissionTreeAll().then(res => {
commit('SET_PERMISSION_TREE_ALL', res.data)
resolve(res.data)
}).catch(err => {
reject(err)
})
})
},
} }
......
...@@ -8,6 +8,7 @@ export const title = [{ ...@@ -8,6 +8,7 @@ export const title = [{
prop: "keyword", prop: "keyword",
label: "关键词", label: "关键词",
columnAlign: 'center', columnAlign: 'center',
showOverFlowToolTip: true,
}, },
{ {
prop: "type", prop: "type",
......
...@@ -13,51 +13,16 @@ ...@@ -13,51 +13,16 @@
</div> </div>
<div class="dialog-content"> <div class="dialog-content">
<el-form :model="dialogForm" class="basic-info"> <el-form :model="dialogForm" class="basic-info">
<el-form-item label="名称" :label-width="formLabelWidth"> <el-form-item label="角色名称" :label-width="formLabelWidth">
<el-input <el-input
v-model="dialogForm.name" v-model="dialogForm.name"
autocomplete="off" autocomplete="off"
placeholder="请输入文献名称" placeholder="请输入角色名称"
></el-input> ></el-input>
</el-form-item> </el-form-item>
<el-form-item label="作者" :label-width="formLabelWidth">
<el-input
v-model="dialogForm.authors"
autocomplete="off"
placeholder="请输入作者"
></el-input>
</el-form-item>
<el-form-item label="文献来源" :label-width="formLabelWidth">
<el-input
v-model="dialogForm.source"
autocomplete="off"
placeholder="请输入文献来源"
></el-input>
</el-form-item>
<el-form-item label="出版/发布日期" :label-width="formLabelWidth">
<el-date-picker
style="width: 100%"
v-model="dialogForm.date"
type="date"
placeholder="请选择出版/发布日期"
value-format="yyyy-MM-dd"
>
</el-date-picker>
</el-form-item>
<el-form-item label="状态" :label-width="formLabelWidth"> <el-form-item label="状态" :label-width="formLabelWidth">
<el-switch v-model="status"> </el-switch> <el-switch v-model="status"> </el-switch>
</el-form-item> </el-form-item>
<el-form-item label="文件" :label-width="formLabelWidth">
<ManualUploader
:files="files"
:fileLimit="1"
:fileSize="50"
listType="text"
:fileType="['pdf']"
ref="pdf"
/>
</el-form-item>
<el-form-item label="备注" :label-width="formLabelWidth"> <el-form-item label="备注" :label-width="formLabelWidth">
<el-input <el-input
type="textarea" type="textarea"
...@@ -68,6 +33,15 @@ ...@@ -68,6 +33,15 @@
> >
</el-input> </el-input>
</el-form-item> </el-form-item>
<el-form-item label="权限" :label-width="formLabelWidth">
<el-tree
:data="permissionTree"
show-checkbox
:props="props"
@check-change="handleCheckChange"
>
</el-tree>
</el-form-item>
</el-form> </el-form>
</div> </div>
<div class="dialog-footer"> <div class="dialog-footer">
...@@ -80,15 +54,9 @@ ...@@ -80,15 +54,9 @@
</template> </template>
<script> <script>
import { addLiterature, editLiterature } from "@/api/literature"; import { addRole, editRole, getPermissionTreeAll,getPermissionById } from "@/api/user";
import ManualUploader from "@/components/Uploader/ManualUploader.vue";
import { mapGetters } from "vuex";
import { uploadFile } from "@/utils/file";
export default { export default {
name: "InfoEditDialog", name: "InfoEditDialog",
components: {
ManualUploader,
},
props: { props: {
visible: { visible: {
type: Boolean, type: Boolean,
...@@ -100,29 +68,27 @@ export default { ...@@ -100,29 +68,27 @@ export default {
}, },
}, },
computed: { computed: {
...mapGetters(["userInfo"]),
title() { title() {
if (this.dialogForm.literatureId) { if (this.dialogForm.id) {
return "修改文献"; return "修改角色信息";
} else { } else {
return "添加文献"; return "添加新角色";
} }
}, },
}, },
watch: { watch: {
form: { form: {
handler: function (value) { handler: function (value) {
debugger
let that = this; let that = this;
that.dialogForm = JSON.parse(JSON.stringify(value)); that.dialogForm = JSON.parse(JSON.stringify(value));
// 编辑状态 // 编辑状态
if (that.dialogForm.literatureId) { if (that.dialogForm.id) {
// 回填状态 // 回填状态
that.status = Boolean(Number(that.dialogForm.status)); that.status = Boolean(Number(that.dialogForm.status));
// 回填文件
if (that.dialogForm.files) { // let perm = await getPermissionById
that.files = that.dialogForm.files; that.getPer()
}
} }
}, },
immediate: true, immediate: true,
...@@ -143,8 +109,21 @@ export default { ...@@ -143,8 +109,21 @@ export default {
status: false, status: false,
files: [], //文献文件 files: [], //文献文件
dialogVisible: false, dialogVisible: false,
permissionTree: [],
props: {
value: "id",
label: "title",
children: "children",
checkStrictly: true,
},
}; };
}, },
async created() {
let res = await getPermissionTreeAll();
this.permissionTree = res.data
console.log(this.permissionTree);
// console.log(res);
},
methods: { methods: {
handlePreview({ type, file }) { handlePreview({ type, file }) {
console.log(type, file); console.log(type, file);
...@@ -160,30 +139,16 @@ export default { ...@@ -160,30 +139,16 @@ export default {
async handleSubmit() { async handleSubmit() {
let params = JSON.parse(JSON.stringify(this.dialogForm)); let params = JSON.parse(JSON.stringify(this.dialogForm));
// 回填文件
let file = this.$refs.pdf.getFiles();
let formData = new FormData();
if (file[0].status == "ready") {
formData.append("files", file[0].raw);
let upLoadRes = await uploadFile(formData);
if (upLoadRes.code == 0) {
params.pdfFile = upLoadRes.data[0].fileId;
} else {
this.$message.error("上传失败!:" + upLoadRes.data.msg);
}
} else if (file[0].status == "success") {
params.pdfFile = file[0].fileId;
}
// 修改状态 // 修改状态
params.status = this.status ? 1 : 0; params.status = this.status ? 1 : 0;
if (params.literatureId) { if (params.literatureId) {
let res = await editLiterature(params); let res = await editRole(params);
if (res.code == 0) { if (res.code == 0) {
this.$message.success("修改成功!"); this.$message.success("修改成功!");
this.reload(); this.reload();
} }
} else { } else {
let res = await addLiterature(params); let res = await addRole(params);
if (res.code == 0) { if (res.code == 0) {
this.$message.success("添加成功!"); this.$message.success("添加成功!");
this.reload(); this.reload();
...@@ -204,6 +169,16 @@ export default { ...@@ -204,6 +169,16 @@ export default {
}) })
.catch((_) => {}); .catch((_) => {});
}, },
handleCheckChange(data, checked, indeterminate) {
console.log(data, checked, indeterminate);
},
async getPer(){
let res = await getPermissionById(this.dialogForm.id)
debugger
console.log(res);
}
}, },
}; };
</script> </script>
......
...@@ -38,6 +38,14 @@ ...@@ -38,6 +38,14 @@
clearable clearable
></el-input> ></el-input>
</el-form-item> </el-form-item>
<el-form-item label="昵称" :label-width="formLabelWidth">
<el-input
v-model="dialogForm.nickName"
autocomplete="off"
placeholder="请输入昵称"
clearable
></el-input>
</el-form-item>
<el-form-item label="真实姓名" :label-width="formLabelWidth"> <el-form-item label="真实姓名" :label-width="formLabelWidth">
<el-input <el-input
v-model="dialogForm.realName" v-model="dialogForm.realName"
...@@ -49,7 +57,7 @@ ...@@ -49,7 +57,7 @@
<el-form-item label="所属部门" :label-width="formLabelWidth"> <el-form-item label="所属部门" :label-width="formLabelWidth">
<el-cascader <el-cascader
style="width: 100%" style="width: 100%"
v-model="dialogForm.deptNo" v-model="dialogForm.deptId"
:options="orgTreeData" :options="orgTreeData"
:props="optionProps" :props="optionProps"
placeholder="请选择所属部门" placeholder="请选择所属部门"
...@@ -113,6 +121,8 @@ export default { ...@@ -113,6 +121,8 @@ export default {
if (that.dialogForm.id) { if (that.dialogForm.id) {
// 回填状态 // 回填状态
that.status = Boolean(Number(that.dialogForm.status)); that.status = Boolean(Number(that.dialogForm.status));
// 回填部门
that.dialogForm.deptId = [that.dialogForm.deptId];
} }
}, },
immediate: true, immediate: true,
...@@ -132,7 +142,7 @@ export default { ...@@ -132,7 +142,7 @@ export default {
data() { data() {
var validatePass = (rule, value, callback) => { var validatePass = (rule, value, callback) => {
if (value === "") { if (value === "") {
callback(new Error("请输入密码")); callback(new Error("请输入密码"));
} else { } else {
var pattern = var pattern =
/^(?![a-zA-Z]+$)(?![A-Z0-9]+$)(?![A-Z\\W_!@#$%^&*`~()-+=]+$)(?![a-z0-9]+$)(?![a-z\\W_!@#$%^&*`~()-+=]+$)(?![0-9\\W_!@#$%^&*`~()-+=]+$)[a-zA-Z0-9\\W_!@#$%^&*`~()-+=]{8,30}$/; /^(?![a-zA-Z]+$)(?![A-Z0-9]+$)(?![A-Z\\W_!@#$%^&*`~()-+=]+$)(?![a-z0-9]+$)(?![a-z\\W_!@#$%^&*`~()-+=]+$)(?![0-9\\W_!@#$%^&*`~()-+=]+$)[a-zA-Z0-9\\W_!@#$%^&*`~()-+=]{8,30}$/;
...@@ -142,7 +152,7 @@ export default { ...@@ -142,7 +152,7 @@ export default {
"密码长度至少8位,至少含数字,大写字母,小写字母,特殊符其中三种" "密码长度至少8位,至少含数字,大写字母,小写字母,特殊符其中三种"
) )
); );
} }
callback(); callback();
} }
}; };
...@@ -247,7 +257,11 @@ export default { ...@@ -247,7 +257,11 @@ export default {
// 修改状态 // 修改状态
params.status = this.status ? 1 : 0; params.status = this.status ? 1 : 0;
console.log(22, params); console.log(22, params);
return; // return;
// 处理馆藏单位
if (params.deptId instanceof Array) {
params.deptId = params.deptId[params.deptId.length - 1];
}
if (params.id) { if (params.id) {
let res = await upadateUser(params); let res = await upadateUser(params);
if (res.code == 0) { if (res.code == 0) {
......
...@@ -2,214 +2,250 @@ ...@@ -2,214 +2,250 @@
<div class="users app-container"> <div class="users app-container">
<el-row :gutter="16"> <el-row :gutter="16">
<el-col :span="6"> <el-col :span="6">
<el-tree :data="treeData" :props="defaultProps" @node-click="handleNodeClick" default-expand-all <el-tree
:expand-on-click-node="false"></el-tree> :data="treeData"
:props="defaultProps"
@node-click="handleNodeClick"
default-expand-all
:expand-on-click-node="false"
></el-tree>
</el-col> </el-col>
<el-col :span="18"> <el-col :span="18">
<div class="top-bar"> <div class="top-bar">
<SearchBar :config="searchConfig" @search="search" @reset="reset" /> <SearchBar :config="searchConfig" @search="search" @reset="reset" />
<el-button type="primary" @click.native="handleOperation({ type: 'add' })" icon="el-icon-s-promotion"> <el-button
新增</el-button> type="primary"
@click.native="handleOperation({ type: 'add' })"
icon="el-icon-s-promotion"
>
新增</el-button
>
</div> </div>
<TablePage :data="list.records" :tableTitle="tableTitle" :operates="tableOperates"> <TablePage
:data="list.records"
:tableTitle="tableTitle"
:operates="tableOperates"
>
<template v-slot:status="data"> <template v-slot:status="data">
<el-popconfirm :title="getStatusTitle(data.scope.status)" @onConfirm="handleChangeStatus(data.scope)"> <el-popconfirm
<el-switch slot="reference" :value="Boolean(Number(data.scope.status))"></el-switch> :title="getStatusTitle(data.scope.status)"
@onConfirm="handleChangeStatus(data.scope)"
>
<el-switch
slot="reference"
:value="Boolean(Number(data.scope.status))"
></el-switch>
</el-popconfirm> </el-popconfirm>
</template> </template>
<template v-slot:operates="scope"> <template v-slot:operates="scope">
<TableOperation :operations="tableOperations" :rawData="scope.scope.row" @handleOperation="handleOperation"> <TableOperation
:operations="tableOperations"
:rawData="scope.scope.row"
@handleOperation="handleOperation"
>
</TableOperation> </TableOperation>
</template> </template>
</TablePage> </TablePage>
<el-pagination @size-change="handleSizeChange" @current-change="handleCurrentChange" <el-pagination
:current-page="Number(list.current)" :page-sizes="[10, 20, 40, 50]" :page-size="Number(list.size)" @size-change="handleSizeChange"
layout="total, sizes, prev, pager, next, jumper" :total="Number(list.total)" class="pagination"> @current-change="handleCurrentChange"
:current-page="Number(list.current)"
:page-sizes="[10, 20, 40, 50]"
:page-size="Number(list.size)"
layout="total, sizes, prev, pager, next, jumper"
:total="Number(list.total)"
class="pagination"
>
</el-pagination> </el-pagination>
</el-col> </el-col>
</el-row> </el-row>
<InfoEditDialog :visible="dialogVisible" :form="form" :orgTreeData="treeData" @handleClose="handleClose" <InfoEditDialog
@refresh="loadListData" /> :visible="dialogVisible"
:form="form"
:orgTreeData="treeData"
@handleClose="handleClose"
@refresh="loadListData"
/>
</div> </div>
</template> </template>
<script> <script>
import TablePage from "@/components/Table/TablePage.vue"; import TablePage from "@/components/Table/TablePage.vue";
import TableOperation from "@/components/Table/TableOperation.vue"; import TableOperation from "@/components/Table/TableOperation.vue";
import SearchBar from "@/components/SearchBar"; import SearchBar from "@/components/SearchBar";
import { title, operates, operations } from "./config"; import { title, operates, operations } from "./config";
import { getDeptTree, getUserList } from "@/api/user"; import { getDeptTree, getUserList, deleteUser } from "@/api/user";
import InfoEditDialog from "./components/InfoEditDialog.vue"; import InfoEditDialog from "./components/InfoEditDialog.vue";
export default { export default {
components: { components: {
TablePage, TablePage,
TableOperation, TableOperation,
SearchBar, SearchBar,
InfoEditDialog, InfoEditDialog,
},
computed: {
tableTitle() {
return title;
}, },
computed: { tableOperates() {
tableTitle() { return operates;
return title; },
tableOperations() {
return operations;
},
getStatusTitle(status) {
return (status) => {
if (status) {
return "是否确定要弃用?";
} else {
return "是否确定要启用?";
}
};
},
},
data() {
return {
treeData: [],
defaultProps: {
children: "children",
label: "label",
}, },
tableOperates() { list: {
return operates; records: [],
size: 10,
current: 1,
total: 0,
}, },
tableOperations() { searchConfig: [
return operations; {
prop: "username",
type: "input",
label: "账号",
},
{
prop: "phone",
type: "input",
label: "手机号",
},
],
currentDeptNo: null,
form: {
username: "", //用户名
nickname: "", //昵称
password: "", //密码
phone: "", //手机号
realName: "", //真实姓名
deptId: "",
// sex:1,//1-男性 2-女性
status: 0, //启用状态
}, },
getStatusTitle(status) { dialogVisible: false,
return (status) => { };
if (status) { },
return '是否确定要弃用?' mounted() {
} else { this.loadTreeData();
return '是否确定要启用?' },
} methods: {
} // 加载树结构数据
async loadTreeData() {
const res = await getDeptTree();
console.log(111, res);
if (res.code == 0) {
this.treeData = res.data;
this.currentDeptNo = this.treeData[0].deptNo;
this.loadListData();
} }
}, },
data() { // 加载表格数据
return { async loadListData() {
treeData: [], var params = {
defaultProps: { page: this.list.current,
children: "children", limit: this.list.size,
label: "label", deptNo: this.currentDeptNo,
},
list: {
records: [],
size: 10,
current: 1,
total: 0,
},
searchConfig: [
{
prop: "username",
type: "input",
label: "用户名",
},
{
prop: "phone",
type: "input",
label: "手机号",
},
],
currentDeptNo: null,
form: {
username: "", //用户名
nickname: "", //昵称
password: "", //密码
phone: "", //手机号
realName: "", //真实姓名
deptNo: "",
// sex:1,//1-男性 2-女性
status: 0,//启用状态
},
dialogVisible: false
}; };
const res = await getUserList(params);
if (res.code == 0) {
this.list = res.data;
}
}, },
mounted() {
this.loadTreeData();
},
methods: {
// 加载树结构数据
async loadTreeData() {
const res = await getDeptTree();
console.log(111, res);
if (res.code == 0) {
this.treeData = res.data;
this.currentDeptNo = this.treeData[0].deptNo;
this.loadListData();
}
},
// 加载表格数据
async loadListData() {
var params = {
page: this.list.current,
limit: this.list.size,
deptNo: this.currentDeptNo,
};
const res = await getUserList(params);
if (res.code == 0) {
this.list = res.data;
}
},
async search(form) { async search(form) {
var params = { var params = {
page: this.list.current, page: this.list.current,
limit: this.list.size, limit: this.list.size,
deptNo: this.currentDeptNo, deptNo: this.currentDeptNo,
...form, ...form,
}; };
const res = await getUserList(params); const res = await getUserList(params);
if (res.code == 0) { if (res.code == 0) {
this.list = res.data; this.list = res.data;
} }
}, },
reset() { reset() {
this.loadListData(); this.loadListData();
}, },
handleNodeClick(e) { handleNodeClick(e) {
const { deptNo } = e; const { deptNo } = e;
this.currentDeptNo = deptNo; this.currentDeptNo = deptNo;
this.loadListData(); this.loadListData();
}, },
// 改变页容量 // 改变页容量
handleSizeChange(value) { handleSizeChange(value) {
this.list.size = value; this.list.size = value;
this.loadListData(); this.loadListData();
}, },
// 改变当前显示页 // 改变当前显示页
handleCurrentChange(value) { handleCurrentChange(value) {
this.list.current = value; this.list.current = value;
this.loadListData(); this.loadListData();
}, },
async handleOperation(value, row) { async handleOperation(value, row) {
console.log("handleOperation", value, row); console.log("handleOperation", value, row);
switch (value.type) { switch (value.type) {
case "add": case "add":
this.dialogVisible = true; this.dialogVisible = true;
break; break;
case "edit": case "edit":
this.form = row; this.form = row;
this.dialogVisible = true; this.dialogVisible = true;
break; break;
case "delete": case "delete":
// let deleteRes = await deleteLt([row.literatureId]); let deleteRes = await deleteUser([row.id]);
// if (deleteRes.code == 0) { if (deleteRes.code == 0) {
// this.$message.success("删除成功!"); this.$message.success("删除成功!");
// this.loadData(); this.loadListData();
// } }
break; break;
} }
}, },
handleClose() { handleClose() {
this.dialogVisible = false; this.dialogVisible = false;
this.form = { this.form = {
status: 0, status: 0,
}; };
},
}, },
}; },
};
</script> </script>
<style lang="scss" scoped> <style lang="scss" scoped>
.top-bar { .top-bar {
display: flex; display: flex;
justify-content: space-between; justify-content: space-between;
align-items: flex-end; align-items: flex-end;
margin-bottom: 10px; margin-bottom: 10px;
} }
.pagination { .pagination {
margin: 16px; margin: 16px;
} }
.el-button { .el-button {
margin-bottom: 22px; margin-bottom: 22px;
} }
</style> </style>
\ No newline at end of file
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论