reactjs 想在react中的map函数内部创建一个通用方法

vh0rcniy  于 2023-01-17  发布在  React
关注(0)|答案(1)|浏览(134)

下面是我的代码

const newState = permissionData.map(obj => {
      if (obj.component.includes('Client')) {
        if ((permissionName.includes('Client')) && (name.includes('create'))) {
          return { ...obj, createPermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Client')) && (name.includes('view'))) {
          return { ...obj, viewPermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Client')) && (name.includes('delete'))) {
          return { ...obj, deletePermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Client')) && (name.includes('update'))) {
          return { ...obj, updatePermission: event.target.checked ? 1 : 0 };
        }
      }

      if (obj.component.includes('Project')) {
        if ((permissionName.includes('Project')) && (name.includes('create'))) {
          return { ...obj, createPermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Project')) && (name.includes('view'))) {
          return { ...obj, viewPermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Project')) && (name.includes('delete'))) {
          return { ...obj, deletePermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Project')) && (name.includes('update'))) {
          return { ...obj, updatePermission: event.target.checked ? 1 : 0 };
        }
      }

      if (obj.component.includes('Schema')) {
        if ((permissionName.includes('Schema')) && (name.includes('create'))) {
          return { ...obj, createPermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Schema')) && (name.includes('view'))) {
          return { ...obj, viewPermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Schema')) && (name.includes('delete'))) {
          return { ...obj, deletePermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Schema')) && (name.includes('update'))) {
          return { ...obj, updatePermission: event.target.checked ? 1 : 0 };
        }
      }

      if (obj.component.includes('Dataset')) {
        if ((permissionName.includes('Dataset')) && (name.includes('create'))) {
          return { ...obj, createPermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Dataset')) && (name.includes('view'))) {
          return { ...obj, viewPermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Dataset')) && (name.includes('delete'))) {
          return { ...obj, deletePermission: event.target.checked ? 1 : 0 };
        }
        if ((permissionName.includes('Dataset')) && (name.includes('update'))) {
          return { ...obj, updatePermission: event.target.checked ? 1 : 0 };
        }
      }
      return obj;
    });

上面的代码运行良好,但是由于代码是重复的,我想做一个通用的方法来优化代码。
但不知道该怎么做。
我在尝试这样的事情-

const checkPermission = (obj: object, type: string, permissionName: string, name: string, checked: boolean) => {
  if (obj.component.includes(type)) {
    if ((permissionName.includes(type)) && (name.includes('create'))) {
      return { ...obj, createPermission: checked };
    }
    if ((permissionName.includes(type)) && (name.includes('view'))) {
      return { ...obj, viewPermission: checked };
    }
    if ((permissionName.includes(type)) && (name.includes('delete'))) {
      return { ...obj, deletePermission: checked };
    }
    if ((permissionName.includes(type)) && (name.includes('update'))) {
      return { ...obj, updatePermission: checked };
    }
  }
};

我把这个方法叫做-
checkPermission(对象,"客户端",权限名称,名称,事件.目标.已检查);
但是它不起作用。有什么建议/想法吗?

cigdeys3

cigdeys31#

['Client', 'Project', 'Schema', 'Dataset']字符串的用法完全相同,因此将它们放入一个数组中,.find是与.includes条件匹配的字符串,这样就消除了一维的重复性。
然后,通过类似地迭代['create', 'view', 'delete', 'update']数组,可以找到正确的操作,这样就可以用括号标记法更新state对象的属性。

const newState = permissionData.map(obj => {
    const entity = ['Client', 'Project', 'Schema', 'Dataset'].find(str => obj.component.includes(str));
    if (!entity || !permissionName.includes(entity)) {
        return obj;
    }
    const action = ['create', 'view', 'delete', 'update'].find(a => name.includes(a));
    return action
        ? { ...obj, [action + 'Permission']: event.target.checked ? 1 : 0 }
        : obj;
});

如果可能的话,您可以考虑更好的状态结构-例如,而不是

{
  createPermission: 1
  // other possible Permission keys
}

如果对象不包含除Permission键以外的任何键,则Permission后缀不会添加任何有用的信息-重命名state数组变量名以包含Permission,这样就不必再使用带括号表示法的丑陋查找。
如果对象 * 可以 * 包含非Permission键,则考虑将其更改为Permission作为子属性。如果Permission值只能为0或1,则使用布尔值可能更合适。

{
  // state properties...

  // and also
  permissions: {
    create: true
    // etc
  }
}

或者具有一组已启用的权限。

permissions: ['create']

或者,如果只有一个可能,则为单个字符串。

permissions: 'create'

相关问题