在 react.js 中创建非渲染包装器组件

Creating a non-rendered wrapper component in react.js

我想创建一个进行安全检查的 React 组件,如果通过,它将渲染它的子项,如果失败,则不会渲染任何内容。

我搭建了一个这样的组件:

var RolesRequired = React.createClass({
    permitted: roles => ...,

    render: function () {
        if (!this.permitted(this.props.roles)) {
            return null;
        }

        return this.props.children;
    }
});

我计划的用法是这样的:

<RolesRequired roles={['admin']}>
    <h1>Welcome to the admin</h1>
    <div>
        Admin stuff here
    </div>
</RolesRequired>

return RolesRequired 组件中的所有子项如何?

我想到了这个解决方案:

var RolesRequired = React.createClass({
    permitted: roles => ...,

    render: function () {
        if (!this.permitted(this.props.roles)) {
            return null;
        }

        return <div>{this.props.children}</div>;
    }
});

我正在做的是将返回的 children 包装在 <div> 中,但我必须添加一个 unwanted/unneeded DOM 元素来实现它。

我认为高阶组件 (HOC) 也是一个很好的选择。您基本上可以将定义某些行为的 HOC 中的任何组件包装起来,并决定它是否应该呈现 wrappe.

最好的方法是使用启用了某些 ES2016 功能(即装饰器)的 ES2015 转译器:

function withRoles(roles) {
  return function(Component) {
    return class ComponentWithRoles extends React.Component {
      constructor(props) {
        super(props)
        // Not sure where the data to get your roles about current user?
        // from but you could potentially to that here if I'm getting your point
        // and also setup listeners
        this.state = { currentUser: 'admin' }
      }

      validateRoles() {
        // you have access to the ``roles`` variable in this scope
        // you can use it to validate them.
        return true;
      }

      render() {
        if (this.validateRoles()) {
          return <Component {...this.props} />;
          )
        } else {
          return <div>Nope...</div>;
        }
      }
    }
  }
}

// You can then use this on any component as a decorator
@withRoles({ showOnlyFor: [ 'admin' ] })
class AdminOnlyComponent extends React.Component {
  render() {
    return <div> This is secert stuff </div>
  }
}

我使用了 ES2016 特性,因为我认为它更容易理解,但你可以通过简单的函数包装来实现它,这是 React 核心成员之一关于 HOC 主题的要点: https://gist.github.com/sebmarkbage/ef0bf1f338a7182b6775