【问题标题】:Designing and structuring a multirole ReactJS application设计和构建多角色 ReactJS 应用程序
【发布时间】:2015-11-15 16:20:28
【问题描述】:

我正在构建一个与 reactJS 中的一些 API 对话的 Web 应用程序。

我的应用有 4 个角色,admin、master、slave、baby。

每个角色都可以比其他角色看到更多的东西,因此菜单和视图在它们之间略有不同。

例如

The navbar has:

for the admin: 5 buttons
for the master: 4 buttons
for the salve: 3 buttons
for the baby: 2 buttons

我想知道构建此应用程序的最佳实践是什么:

我应该有 4 个不同的应用程序吗?这样组件就很清楚了,但是每次我需要实现一个新功能时,我都必须修改 4 个应用程序。

如果这是唯一的方法,我如何在登录后根据角色调用正确的应用程序?

【问题讨论】:

    标签: javascript architecture reactjs


    【解决方案1】:

    拥有四个具有大量重叠代码/功能的独立应用肯定不是最好的方法;这会导致很多不必要的重复。

    如果不同的角色只是添加/删除小的特性和功能,我只会将这些元素的渲染包装在条件中。例如:

    renderAdminButton: function() {
       ( if this.props.user.role === 'admin' ) {
          return (
             <button />
          );
       }
    }
    

    然后将在父应用/组件的 render 函数中调用此函数。

    但是,如果您真的想为每个角色创建一个单独的应用程序,您可以使用类似于以下的函数有条件地渲染该应用程序:

    renderApp: function() {
       var apps = {
          admin: AdminApp,
          master: MasterApp,
          slave: SlaveApp,
          baby: BabyApp
       };
    
       return apps[this.props.user.role];
    }
    

    【讨论】:

      【解决方案2】:

      在您的按钮组件中检查 this.props.hide 并返回 null。

          render() {
              if (this.props.hide) {return null;}
              return (
                  <button>
                      {this.props.btn.text}
                  </button>
              );
          }
      

      在你的父组件中包含每个按钮隐藏属性的逻辑。

          render() {
              var hideAdminBtn = this.props.appState.userRole != 'admin';
              return (
                  <JButton hide={hideAdminBtn} />
              );
          }
      

      【讨论】:

        【解决方案3】:

        您需要将每个访问类型设置为 prop,以便您可以根据收到的 prop 类型呈现应用程序,最好是 componentDidMount()。然后,您可以拥有一个MasterView,它将接收道具并相应地决定要渲染哪个视图。代码将如下所示:

        var MasterView = React.createClass({
          var roleType = this.props.role;
          render: function() {
            if(roleType === 'admin') {
              return (
                <AdminView />
              );
           }
        });  
        

        至于您对实现新功能的关注,您应该将视图和逻辑分解为简单且可重用的组件。例如,您的所有访问类型都可以共享一个公共的&lt;Header /&gt;&lt;Footer /&gt; 组件以及&lt;Profile /&gt; &lt;Settings /&gt; 等。请注意,这些可以进一步细分,以便当您对任何组件进行小的更改时它将传播到您的所有观点。类似的原则也适用于您的逻辑。记得保持干燥


        编辑:

        假设该应用是为商店制作的。通过该门户显示的所有数据(由组件名称表示)是:

        <EmployeeProfile />
        <EmployeeSalary />
        <BuyerRecords />
        <BalanceSheet />
        <Inventory />
        <Billing />
        

        现在让我们定义每个角色的访问级别:

        • 管理员可以访问应用的所有功能。
        • 老板可以查看除员工工资以外的所有详细信息。
        • Slave 可以访问买方的记录、库存和计费。
        • 孩子只能查看库存和计费部分。

        现在,将定义这 6 个广泛的组件,并且肯定会包含多个组件。只要确保每当您觉得视图的特定部分将在其他地方使用时,请继续并将其制成一个单独的组件。

        最后,角色应该像这样呈现:

        var AdminView = React.createClass({
          render: function() {
           return ( 
             <div>
                <EmployeeProfile />
                <EmployeeSalary />
                <BuyerRecords />
                <BalanceSheet />
                <Inventory />
                <Billing />
             </div>
           );
          }
        });
        
        var MasterView = React.createClass({
          render: function() {
           return ( 
             <div>
                <EmployeeProfile />
                <BuyerRecords />
                <BalanceSheet />
                <Inventory />
                <Billing />
             </div>
           );
          }
        });
        
        
        var SlaveView = React.createClass({
          render: function() {
           return ( 
             <div>
                <BuyerRecords />
                <BalanceSheet />
                <Billing />
             </div>
           );
          }
        });
        
        var ChildView = React.createClass({
          render: function() {
           return ( 
             <div>
                <Inventory />
                <Billing />
             </div>
           );
          }
        });
        

        这样你就有 4 个父组件来处理所有的视图。它们由多个组件组成,如果需要进行更改,只需进行一次,它将反映在所有角色中。

        如果您决定为每个角色稍微修改&lt;Inventory /&gt;,您可以选择根据角色来渲染&lt;Inventory /&gt; 的不同子组件。

        去看看这个官方blog post 以及。应该有助于消除任何疑问:)

        【讨论】:

        • 如果我理解错了,这与拥有 4 个应用程序基本相同。以你为例,我需要 4 个不同的 Header 组件,4 个 Profile .... 对吗?
        • 没有。您将拥有 4 个组件,&lt;AdminView /&gt;&lt;MasterView /&gt;&lt;SlaveView /&gt;&lt;BabyView /&gt;,每个组件都将具有相同的页眉或页脚组件。您只需要编写一次这些可重用的组件并将它们包含在您的任何父组件中,例如render: function() { return ( &lt;div&gt;&lt;Header /&gt;&lt;YourAcessSpecificView /&gt; &lt;Footer /&gt;&lt;/div&gt; ); }
        • 但我什至在页眉和页脚方面也存在差异。每个视图都由许多组件组成,每个视图都有角色可以看到的东西,而其他的则不能。所以我认为您的解决方案与拥有 4 个应用程序没有什么不同。
        • @ciaoben 编辑了答案,希望这能更好地解释这个概念。
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-07-19
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-04-30
        • 2010-10-06
        相关资源
        最近更新 更多