Role management basic functions & permission display settings

Basic functions of role management

  1. First create a role.vue in sys under views, copy the content of user.vue in and modify the corresponding position.

    <template>
      <div>
        <!-- Search Bar -->
        <el-card class="box-card" id="search">
          <el-row>
            <el-col :span="20">
              <el-input
                v-model="searchModel.rolename"
                placeholder="role name"
              ></el-input>
              <el-button
                @click="getRoleList"
                type="primary"
                round
                icon="el-icon-search"
                >Query</el-button
              >
            </el-col>
            <el-col :span="4" align="right">
              <el-button
                @click="openEditUI(null)"
                type="primary"
                icon="el-icon-plus"
                circle
                >Add</el-button
              >
            </el-col>
          </el-row>
        </el-card>
    
        <!-- query result list -->
        <el-card>
          <el-table :data="roleList" stripe style="width: 100%">
            <el-table-column label="serial number" width="80">
              <template slot-scope="scope">
                {<!-- -->{
                  (searchModel.pageNo - 1) * searchModel.pageSize + scope.$index + 1
                }}
              </template>
            </el-table-column>
            <el-table-column
              prop="roleId"
              label="Role ID"
              width="200"
            ></el-table-column>
            <el-table-column
              prop="roleName"
              label="role name"
              width="260"
            ></el-table-column>
            <el-table-column prop="roleDesc" label="description"></el-table-column>
            <el-table-column label="Operation" width="180">
              <template slot-scope="scope">
                <el-button
                  type="primary"
                  @click="openEditUI(scope.row.roleId)"
                  icon="el-icon-edit"
                  circle
                  size="mini"
                ></el-button>
                <el-button
                  type="danger"
                  @click="deleteRole(scope.row)"
                  icon="el-icon-delete"
                  circle
                  size="mini"
                ></el-button>
              </template>
            </el-table-column>
          </el-table>
        </el-card>
    
        <!-- Pagination component -->
        <el-pagination
          @size-change="handleSizeChange"
          @current-change="handleCurrentChange"
          :current-page="searchModel.pageNo"
          :page-sizes="[5, 10, 20, 40]"
          :page-size="searchModel.pageSize"
          layout="total, sizes, prev, pager, next, jumper"
          :total="total"
        ></el-pagination>
    
        <!-- Role information editing dialog box -->
        <el-dialog
          @close="clearForm"
          :title="title"
          :visible.sync="dialogFormVisible"
        >
          <el-form :model="roleForm" :rules="rules" ref="roleFormRef">
            <el-form-item
              label="role name"
              prop="roleName"
              :label-width="formLabelWidth"
            >
              <el-input v-model="roleForm.roleName" autocomplete="off"></el-input>
            </el-form-item>
            <el-form-item
              label="role description"
              prop="roleDesc"
              :label-width="formLabelWidth"
            >
              <el-input v-model="roleForm.roleDesc" autocomplete="off"></el-input>
            </el-form-item>
            <el-form-item
              label="Permission Settings"
              prop="menuIdList"
              :label-width="formLabelWidth"
            >
              <el-tree :data="menuList" :props="menuProps" show-checkbox style="width:85%" default-expand-all></el-tree>
            </el-form-item>
          </el-form>
          <div slot="footer" class="dialog-footer">
            <el-button @click="dialogFormVisible = false">Cancel</el-button>
            <el-button type="primary" @click="saveRole">OK</el-button>
          </div>
        </el-dialog>
      </div>
    </template>
    
    <script>
    import roleApi from "@/api/roleManage";
    import menuApi from "@/api/menuManage";
    export default {
      data() {
        return {
          menuList:[],
          menuProps: {
            children: "children",
            label: "title",
          },
          formLabelWidth: "130px",
          roleForm: {},
          dialogFormVisible: false,
          total: 0,
          title: "",
          searchModel: {
            pageNo: 1,
            pageSize: 10,
          },
          roleList: [],
          rules: {
            roleName: [
              { required: true, message: "Please enter the character name", trigger: "blur" },
              {
                min: 2,
                max: 20,
                message: "The length is between 2 and 20 characters",
                trigger: "blur",
              },
            ],
            roleDesc: [
              { required: true, message: "Please enter a role description", trigger: "blur" },
              {
                min: 2,
                max: 20,
                message: "The length is between 2 and 20 characters",
                trigger: "blur",
              },
            ],
          },
        };
      },
      methods: {
        getAllMenu(){
          menuApi.getAllMenu().then(respone=>{
            this.menuList=respone.data;
          });
        },
        deleteRole(role) {
          this.$confirm(`Are you sure to delete the role ${role.roleName}?`, "Prompt", {
            confirmButtonText: "OK",
            cancelButtonText: "Cancel",
            type: "warning",
          })
            .then(() => {
              roleApi.deleteRoleById(role.roleId).then((response) => {
                this. $message({
                  type: "success",
                  message: response. message,
                });
                this. getRoleList();
              });
            })
            .catch(() => {
              this. $message({
                type: "info",
                message: "Delete canceled",
              });
            });
        },
        saveRole() {
          //trigger form validation
          this.$refs.roleFormRef.validate((valid) => {
            if (valid) {
              //Submit the request to the background
              roleApi.saveRole(this.roleForm).then((respone) => {
                //success prompt
                this. $message({
                  message: response. message,
                  type: "success",
                });
                //Close the dialog
                this.dialogFormVisible = false;
                // Refresh the form
                this. getRoleList();
              });
            } else {
              console.log("error submit!!");
              return false;
            }
          });
        },
        clearForm() {
          this.roleForm = {};
          this.$refs.roleFormRef.clearValidate();
        },
        openEditUI(id) {
          if (id == null) {
            this.title = "New role";
          } else {
            this.title = "Modify role";
            // query role by id
            roleApi.getRoleById(id).then((response) => {
              this.roleForm = response.data;
            });
          }
          this.dialogFormVisible = true;
        },
        handleSizeChange(pageSize) {
          this.searchModel.pageSize = pageSize;
          this. getRoleList();
        },
        handleCurrentChange(pageNo) {
          this.searchModel.pageNo = pageNo;
          this. getRoleList();
        },
        getRoleList() {
          roleApi.getRoleList(this.searchModel).then((response) => {
            this.roleList = response.data.rows;
            this.total = response.data.total;
          });
        },
      },
      created() {
        this. getRoleList();
        this. getAllMenu();
      },
    };
    </script>
    
    <style>
    #search.el-input {
      width: 200px;
      margin-right: 10px;
    }
    .el-dialog .el-input {
      width: 85%;
    }
    </style>
    
  2. Copy userManager.js as new roleManager.js and modify the content accordingly.

    import request from '@/utils/request'
    
    export default {<!-- -->
      getRoleList(searchModel) {<!-- -->
        return request({<!-- -->
          url: 'sys/role/getlsitrole',
          method: "get",
          params: {<!-- -->
            pageNo: searchModel. pageNo,
            pageSize: searchModel. pageSize,
            rolename: searchModel.rolename,
          }
        });
      },
    
      addRole(role) {<!-- -->
        return request({<!-- -->
          url: 'sys/role/addrole',
          method: "post",
          data: role
        });
      },
    
      getRoleById(id) {<!-- -->
        return request({<!-- -->
          url: `sys/role/${<!-- -->id}`,
          method: "get",
        });
      },
    
      updateRole(role) {<!-- -->
        return request({<!-- -->
          url: 'sys/role/updaterole',
          method: "put",
          data: role
        });
      },
    
      saveRole(role) {<!-- -->
        if (role.roleId == null & amp; & amp; role.roleId == undefined) {<!-- -->
          return this. addRole(role);
        }
        return this. updateRole(role);
      },
    
      deleteRoleById(id) {<!-- -->
        return request({<!-- -->
          url: `sys/role/deleterolebyid/${<!-- -->id}`,
          method: "delete",
        });
      },
    
    }
    
  3. After the front-end settings are complete, complete the corresponding settings in the back-end controller.

    package com.zz.sys.controller;
    
    import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
    import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
    import com.zz.common.vo.Result;
    import com.zz.sys.entity.Role;
    import com.zz.sys.service.IRoleService;
    import io.swagger.annotations.Api;
    import io.swagger.annotations.ApiOperation;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.util.StringUtils;
    import org.springframework.web.bind.annotation.*;
    
    import java.util.HashMap;
    import java.util.Map;
    
    /**
     * <p>
     * Front Controller
     *</p>
     *
     * @author zhongzhong
     * @since 2023-05-09
     */
    @Api(tags = {<!-- -->"role interface list"})
    @RestController
    @RequestMapping("/sys/role")
    public class RoleController {<!-- -->
        @Autowired
        private IRoleService iRoleService;
    
        @GetMapping("/getlsitrole")
        public Result<Map<String, Object>> getListRole(@RequestParam(value = "rolename", required = false) String rolename,
                                                       @RequestParam(value = "pageNo") Long pageNo,
                                                       @RequestParam(value = "pageSize") Long pageSize) {<!-- -->
    
            LambdaQueryWrapper<Role> wrapper = new LambdaQueryWrapper<>();
            wrapper.eq(StringUtils.hasLength(rolename), Role::getRoleName, rolename);
            wrapper.orderByDesc(Role::getRoleId);
    
            Page<Role> rolePage = new Page<>(pageNo, pageSize);
            iRoleService.page(rolePage, wrapper);
    
            Map<String, Object> data = new HashMap<>();
            data.put("total", rolePage.getTotal());
            data.put("rows", rolePage.getRecords());
    
            return Result. success(data);
        }
    
        @PostMapping("/addrole")
        public Result<?> addRole(@RequestBody Role role) {<!-- -->
            iRoleService. save(role);
            return Result.success("Added role successfully");
        }
    
        @PutMapping("/updaterole")
        public Result<?> updateRole(@RequestBody Role role) {<!-- -->
            iRoleService. updateById(role);
            return Result.success("modified role successfully");
        }
    
        @GetMapping("/{id}")
        public Result<Role> getRoleById(@PathVariable("id") Integer id) {<!-- -->
            Role role = iRoleService. getById(id);
            return Result. success(role);
        }
    
        @DeleteMapping("/deleterolebyid/{id}")
        public Result<Role> deleteRoleById(@PathVariable("id") Integer id) {<!-- -->
    
            iRoleService. removeById(id);
            return Result.success("delete user successfully");
        }
    }
    

Role permission setting display

  1. Add a menuManage.js to the front end

    import request from '@/utils/request'
    
    export default {<!-- -->
      getAllMenu() {<!-- -->
        return request({<!-- -->
          url: 'sys/menu/getallmenu',
          method: "get",
        });
      },
    
    }
    
  2. Modify the role information editing dialog box in role.vue and add permission setting content

    <el-form-item
      label="Permission Settings"
      prop="menuIdList"
      :label-width="formLabelWidth"
    >
      <el-tree
        :data="menuList"
        :props="menuProps"
        node-key="menuId"
        show-checkbox
        style="width: 85%"
        default-expand-all
      ></el-tree>
    </el-form-item>
    
  3. Introduce menuManage.js in role.vue, and add a bound content in the return of data():

    menuProps: {
            children: "children",
            label: "title",
          },
    

    Add a method to methods:

    getAllMenu() {
          menuApi.getAllMenu().then((respone) => {
            this.menuList = response.data;
          });
        },
    

    Call this getAllMenu method in created().

  4. Modify the data in the table in the database:

    delete from x_menu;
    insert into `x_menu` (`menu_id`, `component`, `path`, `redirect`, `name`, `title`, `icon`, `parent_id`, `is_leaf`, `hidden`) values(' 1','Layout','/sys','/sys/user','sysManage','system management','userManage','0' ,'N','0');
    insert into `x_menu` (`menu_id`, `component`, `path`, `redirect`, `name`, `title`, `icon`, `parent_id`, `is_leaf`, `hidden`) values(' 2','sys/user','user',NULL,'userList','user list','user','1','Y' ,'0');
    insert into `x_menu` (`menu_id`, `component`, `path`, `redirect`, `name`, `title`, `icon`, `parent_id`, `is_leaf`, `hidden`) values(' 3','sys/role','role',NULL,'roleList','role list','roleManage','1','Y' ,'0');
    insert into `x_menu` (`menu_id`, `component`, `path`, `redirect`, `name`, `title`, `icon`, `parent_id`, `is_leaf`, `hidden`) values(' 4','Layout','/test','/test/test1','test','functional test','form','0' ,'N','0');
    insert into `x_menu` (`menu_id`, `component`, `path`, `redirect`, `name`, `title`, `icon`, `parent_id`, `is_leaf`, `hidden`) values(' 5','test/test1','test1','','test1','test point one','form','4',\ 'Y','0');
    insert into `x_menu` (`menu_id`, `component`, `path`, `redirect`, `name`, `title`, `icon`, `parent_id`, `is_leaf`, `hidden`) values(' 6','test/test2','test2','','test2','test point 2','form','4',\ 'Y','0');
    insert into `x_menu` (`menu_id`, `component`, `path`, `redirect`, `name`, `title`, `icon`, `parent_id`, `is_leaf`, `hidden`) values(' 7','test/test3','test3','','test3','test point three','form','4',\ 'Y','0');
    
  5. Modify the properties of the Menu class in the backend, add two properties, and process the properties.

    @TableField(exist = false)
    @JsonInclude(JsonInclude. Include. NON_EMPTY)
    private List<Menu> children;
    
    @TableField(exist = false)
    private Map<String, Object> meta;
    
    public Map<String, Object> getMeta() {<!-- -->
        meta = new HashMap<>();
        meta. put("title", title);
        meta. put("icon", icon);
        return meta;
    }
    
  6. Add the corresponding method in menuController.

    package com.zz.sys.controller;
    
    import com.zz.common.vo.Result;
    import com.zz.sys.entity.Menu;
    import com.zz.sys.service.IMenuService;
    import io.swagger.annotations.Api;
    import io.swagger.annotations.ApiOperation;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.stereotype.Controller;
    import org.springframework.web.bind.annotation.RestController;
    
    import java.util.List;
    
    /**
     * <p>
     * Front Controller
     *</p>
     *
     * @author zhongzhong
     * @since 2023-05-09
     */
    @Api(tags = {<!-- -->"Privilege Management Interface"})
    @RestController
    @RequestMapping("/sys/menu")
    public class MenuController {<!-- -->
    
        @Autowired
        private IMenuService iMenuService;
    
        @ApiOperation("Query all menu data")
        @GetMapping("/getallmenu")
        public Result<List<Menu>> getAllMenu(){<!-- -->
            List<Menu> menuList=iMenuService. getAllMenu();
            return Result. success(menuList);
        }
    }
    
  7. Handle the reading of menu data in menuServiceImpl:

    package com.zz.sys.service.impl;
    
    import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
    import com.zz.sys.entity.Menu;
    import com.zz.sys.mapper.MenuMapper;
    import com.zz.sys.service.IMenuService;
    import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
    import org.springframework.stereotype.Service;
    
    import java.util.List;
    
    /**
     * <p>
     * Service implementation class
     *</p>
     *
     * @author zhongzhong
     * @since 2023-05-09
     */
    @Service
    public class MenuServiceImpl extends ServiceImpl<MenuMapper, Menu> implements IMenuService {<!-- -->
    
        @Override
        public List<Menu> getAllMenu() {<!-- -->
            //A menu
            LambdaQueryWrapper<Menu> wrapper = new LambdaQueryWrapper<>();
            wrapper.eq(Menu::getParentId,0);
            List<Menu> menuList = this. list(wrapper);
            // Populate the submenu
            setMenuChildren(menuList);
            return menuList;
        }
    
        private void setMenuChildren(List<Menu> menuList) {<!-- -->
            if (menuList !=null){<!-- -->
                for (Menu menu : menuList) {<!-- -->
                    LambdaQueryWrapper<Menu> wrapperSub = new LambdaQueryWrapper<>();
                    wrapperSub.eq(Menu::getParentId, menu.getMenuId());
                    List<Menu> menuListSub = this. list(wrapperSub);
                    menu.setChildren(menuListSub);
                    // recursion
                    setMenuChildren(menuListSub);
                }
            }
        }
    }