Source

components/forms/RoleForm.jsx

import React from 'react';
import FormField from '../ui/FormField';
import Checkbox from '../ui/Checkbox';
import { useForm } from '../../hooks/useForm';

/**
 * RoleForm component for creating or updating roles.
 *
 * @param {object} props - The component props.
 * @param {object} [props.initialData] - Initial data for the form (used for editing).
 * @param {function} props.onSubmit - Callback function when the form is submitted successfully.
 * @param {function} props.onCancel - Callback function when the form is cancelled.
 * @param {boolean} [props.loading=false] - Boolean indicating if the form is currently submitting.
 * @returns {React.Element} The RoleForm component.
 */
const RoleForm = ({ initialData, onSubmit, onCancel, loading }) => {
  /**
 * Custom hook useForm for form state management and validation.
 * Initializes form values with initialData or default values and defines validation rules.
 *
 * @param {object} initialData - Initial values for the form fields.
 * @param {object} validationRules - Rules for validating form fields.
 * @returns {object} An object containing form state and helper functions.
 * @property {object} values - The current form values.
 * @property {object} errors - Validation errors for the form fields.
 * @property {function} handleChange - Handles changes to form input fields.
 * @property {function} handleBlur - Handles blur events on form input fields.
 * @property {function} validate - Validates the current form values.
 */
  const { values, errors, handleChange, handleBlur, validate } = useForm(
    initialData || {
      name: '',
      description: '',
      is_approver: false,
      is_responder: false,
      is_creator: false,
    },
    {
      name: { required: true, minLength: 2 },
    }
  );

  /**
 * Handles the form submission.
 * Prevents the default form submission, validates the form, and calls the onSubmit callback if valid.
 *
 * @param {object} e - The submit event.
 */
  const handleSubmit = (e) => {
    e.preventDefault();
    if (validate()) {
      onSubmit(values);
    }
  };

  /**
 * Renders the RoleForm component.
 * Includes form fields for role name and description, checkboxes for permissions, and action buttons.
 *
 */
  return (
    <form onSubmit={handleSubmit} className="space-y-4">
      <FormField
        label="Role Name"
        name="name"
        value={values.name}
        onChange={handleChange}
        onBlur={handleBlur}
        error={errors.name}
        required
      />

      <FormField
        label="Description"
        name="description"
        type="textarea"
        value={values.description}
        onChange={handleChange}
        onBlur={handleBlur}
        error={errors.description}
        placeholder="Enter role description..."
      />

      <div className="space-y-2">
        <label className="block text-sm font-medium text-gray-700">Permissions</label>
        <Checkbox
          name="is_approver"
          label="Can approve requests"
          checked={values.is_approver}
          onChange={handleChange}
        />
        <Checkbox
          name="is_responder"
          label="Can respond to requests"
          checked={values.is_responder}
          onChange={handleChange}
        />
        <Checkbox
          name="is_creator"
          label="Can create requests"
          checked={values.is_creator}
          onChange={handleChange}
        />
      </div>

      <div className="flex justify-end space-x-2 pt-4">
        <button
          type="button"
          onClick={onCancel}
          className="px-4 py-2 text-sm font-medium text-gray-700 bg-gray-200 rounded-md hover:bg-gray-300"
          disabled={loading}
        >
          Cancel
        </button>
        <button
          type="submit"
          className="px-4 py-2 text-sm font-medium text-white bg-blue-600 rounded-md hover:bg-blue-700 disabled:opacity-50"
          disabled={loading}
        >
          {loading ? 'Saving...' : initialData ? 'Update' : 'Create'}
        </button>
      </div>
    </form>
  );
};

export default RoleForm;