containers/Admin/RoleSettings.js

import React, { Component } from 'react';
import { connect } from 'react-redux';
import {
  aDisableEnableRole,
  aGetPermissions,
  aRemoveRole,
  aRolesInit,
  aSaveEditRole,
  aSaveNewRole,
  aSetPagination,
} from '../../reducers/actions';
import { getPagination, checkPermisson, getSelectedTimezone } from '../../selectors/common';
import {
  getRoles,
  getRoleCreateCallback,
  getPermissions,
  getSelectedRoleId,
  getRolePermissions,
} from '../../selectors/admin';
import SVGComponent from '../../components/SVG/SVGComponent';
import { getCountryDateTime } from '../../utils/common';
import Pagination from '../../components/Pagination';
import { SVG_ICONS, PERMISSIONS, CONFIRM_MODAL_CONTENT } from '../../constants';
import RoleModal from '../../components/MenuItems/Admin/RoleModal';
import RoleMenuModal from '../../components/MenuItems/Admin/RoleMenuModal';
import ConfirmationModal from '../../components/Modals/ConfirmationModal';
import { aRolePermissions } from '../../reducers/admin';
import { aSetFilters } from '../../reducers/common';

const mapToProps = (state) => ({
  roles: getRoles(state),
  pagination: getPagination(state),
  roleCreateCallback: getRoleCreateCallback(state),
  permissions: getPermissions(state),
  selectedRoleId: getSelectedRoleId(state),
  rolePermissions: getRolePermissions(state),
  checkPermisson: (payload) => checkPermisson(state, payload),
  selectedTimezone: getSelectedTimezone(state),
});

const actionsToProps = (dispatch) => ({
  setFilterData: (payload) => dispatch(aSetFilters(payload)),
  getRoles: (payload) => dispatch(aRolesInit(payload)),
  setPagination: (payload) => dispatch(aSetPagination(payload)),
  getPermissions: (payload) => dispatch(aGetPermissions(payload)),
  saveNewRole: (payload) => dispatch(aSaveNewRole(payload)),
  saveEditRole: (payload) => dispatch(aSaveEditRole(payload)),
  getRolePermissions: (payload) => dispatch(aRolePermissions(payload)),
  removeRole: (payload) => dispatch(aRemoveRole(payload)),
  changeRoleStatus: (payload) => dispatch(aDisableEnableRole(payload)),
});

/**
 * @class
 * @property {object} props
 * @property {Array} props.roles All roles data
 * @property {object} props.pagination Pagination settings
 * @property {boolean} props.roleCreateCallback
 * @property {Array} props.permissions All permisions
 * @property {number} props.selectedRoleId Selected role id
 * @property {Array} props.rolePermissions All permissions for one role
 * @property {boolean} props.checkPermisson Check if user have
 *  permission for specific action or view
 * @property {Function} props.setFilterData Filter roles
 * @property {Function} props.getRoles Get roles API
 * @property {Function} props.setPagination Change pagination page
 * @property {Function} props.getPermissions API call to get all permissions
 * @property {Function} props.saveNewRole API call for create new role
 * @property {Function} props.saveEditRole API call for edit role
 * @property {Function} props.getRolePermissions API call to get
 * permissions data for particular role
 * @property {Function} props.removeRole API call to remove one role
 * @property {Function} props.changeRoleStatus API call to change status of role
 */
class RolesSettings extends Component {
  constructor(props) {
    super(props);
    /**
     * @member {object}
     * @property {boolean} roleModalOpen
     * @property {boolean} confirmationModalOpen
     * @property {number} moreModalRoleId
     * @property {object} selectedRole
     * @property {boolean} isEditingRole
     * @property {boolean} isAddNewRole
     * @property {object} modalData
     */
    this.state = {
      roleModalOpen: false,
      confirmationModalOpen: false,
      moreModalRoleId: -1,
      selectedRole: {},
      isEditingRole: false,
      isAddNewRole: false,
      modalData: {},
    };

    /**
     * @member {object}
     */
    this.emptyRole = {
      name: '',
      description: '',
    };
    /**
     * @member {object}
     * @description Check of user have permission for some of actions
     * @property {boolean} add
     * @property {boolean} enableDisable
     * @property {boolean} remove
     * @property {boolean} edit
     */
    this.hasPermissionTo = {
      add: props.checkPermisson(PERMISSIONS.ADMIN_ROLES_ADD),
      enableDisable: props.checkPermisson(PERMISSIONS.ADMIN_ROLES_DISABLE_ENABLE),
      remove: props.checkPermisson(PERMISSIONS.ADMIN_ROLES_REMOVE),
      edit: props.checkPermisson(PERMISSIONS.ADMIN_ROLES_UPDATE),
    };
  }

  /**
   * Get roles and permissions
   *
   * @function
   * @returns {void}
   */
  componentDidMount() {
    this.refreshGrid();
    this.props.getPermissions();
  }

  /**
   * Refresh roles table
   *
   * @function
   * @returns {void}
   */
  refreshGrid = () => {
    this.props.getRoles();
  };

  /**
   * Toggle role menu modal
   *
   * @function
   * @param {object} role Role
   * @returns {void}
   */
  openMoreModal = (role) => {
    if (this.state.moreModalRoleId === role.roleId) {
      this.setState({
        moreModalRoleId: -1,
        selectedRole: role,
      });
    } else {
      this.setState({
        moreModalRoleId: role.roleId,
        selectedRole: role,
      });
    }
  };

  /**
   * Close Role Menu modal
   *
   * @function
   * @returns {void}
   */
  closeMoreModal = () => {
    this.setState({ moreModalRoleId: -1 });
  };

  /**
   * Open add roles modal
   *
   * @function
   * @returns {void}
   */
  openAddRoleModal = () => {
    this.setState({
      roleModalOpen: true,
      isAddNewRole: true,
    });
  };

  /**
   * Open edit role modal
   *
   * @function
   * @returns {void}
   */
  openEditRole = () => {
    this.setState({
      roleModalOpen: true,
      isEditingRole: true,
    });
  };

  /**
   * open confirmation modal function
   *
   * @function
   * @returns {void}
   */
  openConfirmationModal = () => {
    const confirmationRemoveModalData = { ...CONFIRM_MODAL_CONTENT.REMOVE_ROLE };
    confirmationRemoveModalData.additionalMessages = [this.state.selectedRole.name];
    this.setState({
      confirmationModalOpen: true,
      modalData: confirmationRemoveModalData,
    });
  };

  /**
   * Confirm modal for remove role
   *
   * @function
   * @returns {void}
   */
  confirmRemoveRole = () => {
    this.props.removeRole({ roleId: this.state.selectedRole.roleId });
    this.setState({
      confirmationModalOpen: false,
      moreModalRoleId: -1,
    });
  };

  /**
   * Close role modal
   *
   * @function
   * @returns {void}
   */
  closeRoleModal = () => {
    this.setState({
      roleModalOpen: false,
      isEditingRole: false,
      isAddNewRole: false,
      confirmationModalOpen: false,
    });
  };

  /**
   * Render roles rows
   *
   * @function
   * @param {object} role
   * @returns {view}
   */
  renderRolesRows = (role) => {
    const openClass = (role.roleId === this.state.moreModalRoleId) === true ? ' open active ' : '';
    return (
      <tr key={role.roleId} className={`table-style-row ${openClass}`}>
        <td>{role.roleId}</td>
        <td>{role.name}</td>
        <td>{role.description}</td>
        <td>{getCountryDateTime(role.insertionDate, this.props.selectedTimezone)}</td>
        <td>{role.insertionUser}</td>
        <td>{role.status}</td>
        {(this.hasPermissionTo.enableDisable || this.hasPermissionTo.edit || this.hasPermissionTo.remove) && (
          <td className="table-style-icon" onClick={this.openMoreModal.bind(this, role)}>
            <SVGComponent className="icon-xs" src={`${SVG_ICONS.utility}#dots`} />
            <RoleMenuModal
              role={role}
              closeMoreModal={this.closeMoreModal}
              refreshGrid={this.refreshGrid}
              openEditRole={this.openEditRole}
              changeRoleStatus={this.props.changeRoleStatus}
              hasPermissionTo={this.hasPermissionTo}
              openConfirmationModal={this.openConfirmationModal}
            />
          </td>
        )}
      </tr>
    );
  };

  /**
   * Render
   *
   * @returns {view}
   */
  render() {
    const tableFadeClass =
      this.state.moreModalRoleId > 0 || this.state.roleModalOpen === true || this.state.confirmationModalOpen === true
        ? ' fade-effect '
        : '';

    return (
      <>
        <div className="role mt-20">
          <div className="table-wrapper">
            <div className="table-responsive">
              <table className="table-style table-s" id="data-table">
                <thead>
                  <tr>
                    <th>ID</th>
                    <th>Name </th>
                    <th>Description</th>
                    <th>Creation Date</th>
                    <th>Created By</th>
                    <th>Status</th>
                    <td />
                  </tr>
                </thead>
                <tbody>{this.props.roles.map((role) => this.renderRolesRows(role))}</tbody>
              </table>
            </div>
          </div>
          {this.state.roleModalOpen ? (
            <RoleModal
              rolePermissions={this.props.rolePermissions}
              selectedRoleId={this.props.selectedRoleId}
              permissions={this.props.permissions}
              getRolePermissions={this.props.getRolePermissions}
              closeRoleModal={this.closeRoleModal}
              role={this.state.isAddNewRole ? this.emptyRole : this.state.selectedRole}
              isEditingRole={this.state.isEditingRole}
              isAddNewRole={this.state.isAddNewRole}
              saveNewRole={this.props.saveNewRole}
              saveEditRole={this.props.saveEditRole}
            />
          ) : null}
          <div className="pagination-container d-flex justify-content-end align-items-center">
            {this.hasPermissionTo.add && (
              <button
                id="addRoleBtn_roleSettingsPage"
                className="btn btn-primary"
                onClick={this.openAddRoleModal}
                type="button"
              >
                Add role
              </button>
            )}
            {this.props.pagination.totalPage && (
              <Pagination
                {...this.props.pagination}
                paging={this.refreshGrid}
                setPagination={this.props.setPagination}
              />
            )}
          </div>
          {this.state.confirmationModalOpen ? (
            <ConfirmationModal
              modalData={this.state.modalData}
              cancel={this.closeRoleModal}
              openDialog={this.openConfirmationModal}
              confirmation={this.confirmRemoveRole}
            />
          ) : null}
          {(this.state.roleModalOpen || this.state.confirmationModalOpen) && (
            <div className="overlay-mask bg-grey open" />
          )}
        </div>
        {tableFadeClass && <div className="overlay-mask bg-grey open" />}
      </>
    );
  }
}

export default connect(mapToProps, actionsToProps)(RolesSettings);