React后台管理系统-难点1:角色权限展示异常

  • Post author:
  • Post category:其他


我最近在做后台管理系统时碰到了很突然的bug,有必要记录一下这些内容。


Bug

:当我们去点击不同角色去设置其角色权限的时候,弹窗显示的默认勾选的角色权限都是一样的,实际上是不一样的。

在这里插入图片描述
在这里插入图片描述


解决方案

:利用组件的

componentWillReceiveProps()

,它会在接收到

props

后先更新状态再

render

渲染。


componentWillReceiveProps()

是React组件的一个很重要的生命周期函数。组件在初次渲染的时候不会执行该函数,只有当

props

发生变化时才会执行该函数。它会在接收到

props

后先更新状态再

render

渲染。

该函数可以根据属性的变化,通过调用

this.setState()

来更新我们的组件状态,在该函数中调用

this.setState()

将不会引起第二次渲染。

部分关键代码如下:


父组件

  ......
    export default class Role extends Component {
    	state = {
        roles: [], //所有角色的列表
        role: {}, //选中的role
      }; 
    	constructor(props) {
        super(props);
        this.auth = React.createRef();
      }
    	getRoles = async () => {
        const result = await reqRoles();
        if (result.status === 0) {
          const roles = result.data;
          this.setState({ roles });
        } else {
          message.error("获取角色失败!");
        }
      };
      ......
    	render(){
        const { role } = this.state;
        return (
          ......
          <AuthForm ref={this.auth} role={role} /> //父组件传给AuthForm组件一个role对象
          ......
        )
      }
    }


子组件

 import React, { Component } from "react";
    import { Form, Input, Tree } from "antd";
    import PropTypes from "prop-types";
    import menuList from "../../config/menuConfig";
    
    const Item = Form.Item;
    const { TreeNode } = Tree;
    /* 设置角色权限的form组件 */
    export default class AuthForm extends Component {
      static propTypes = {
        role: PropTypes.object, //子组件对接收的参数做类型限制
      };
      /* 根据传入角色的menu生成初始状态 */
      constructor(props) {
        super(props);
        const { menus } = this.props.role; //从接收到的参数role中获取menus
        this.state = { //更新这个组建的状态,这样就可以显示用户所点击的那个角色的权限内容了
          checkedKeys: menus,
        };
      }
      /* 选中某个node时的回调 */
      onCheck = (checkedKeys) => {
        console.log("onCheck", checkedKeys);
        this.setState({ checkedKeys });
      };
      /* 获取角色权限树的节点,成后才才能显示本系统所有的权限内容,供管理员选择 */
      getTreeNodes = (menuList) => { 
        return menuList.reduce((pre, item) => {
          pre.push(
            <TreeNode title={item.title} key={item.key}>
              {item.children ? this.getTreeNodes(item.children) : null}
            </TreeNode>
          );
          return pre;
        }, []);
      };
      getMenus = () => this.state.checkedKeys;
      componentWillMount() { //在组件挂载前获取到权限树,这样用户就可以看到权限树
        this.treeNodes = this.getTreeNodes(menuList);
      }
      /* 根据新传入的role来更新checkedKeys状态
      当组件接收到新的属性时自动调用 */
      //也就是,当用户点击某个角色并点击“设置角色权限”按钮后,所弹出的弹框就会显示指定用户目前的角色权限情况,如果没有这个函数的处理,不论我们点击哪个角色,它们的角色权限列表显示的都是一样的
      componentWillReceiveProps(nextProps) {
        console.log("componentWillReceiveProps()", nextProps);
        const menus = nextProps.role.menus;
        this.setState({
          checkedKeys: menus,
        });
        // this.state.checkedKeys = menus
      }
      /* 渲染 */
      render() {
        console.log("AuthForm render()");
        const { role } = this.props;
        const { checkedKeys } = this.state;
        // const { getFieldDecorator } = this.props.form;
        const formItemLayout = {
          labelCol: { span: 5 },
          wrapperCol: { span: 16 },
        };
        return (
          <Form>
            <Item label="角色名称" {...formItemLayout}>
              <Input value={role.name} disabled />
            </Item>
            <Tree
              onCheck={this.onCheck}
              checkable
              defaultExpandAll={true}
              checkedKeys={checkedKeys}
            >
              <TreeNode title="平台权限" key="all">
                {this.treeNodes}
              </TreeNode>
            </Tree>
          </Form>
        );
      }
    }



版权声明:本文为m0_59183852原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。