All files / libs/assignments/plans/components/src/lib/forms/create-user-plan-assignments CreateUserPlanAssignmentsForm.tsx

100% Statements 76/76
100% Branches 5/5
100% Functions 1/1
100% Lines 76/76

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 771x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 2x 2x 2x 2x 2x 2x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x  
import { memo, useCallback, useMemo } from 'react';
import { useIntl } from 'react-intl';
import { z } from 'zod';
 
import { useUpsertPlanAssignments } from '@amalia/assignments/plans/state';
import { FormikForm, type FormikFormProps } from '@amalia/ext/formik';
import { type Plan, type PlanAssignment } from '@amalia/payout-definition/plans/types';
import { type UserContract } from '@amalia/tenants/users/types';
 
type CreateUserPlanAssignmentsFormValues = {
  planIds: Plan['id'][];
};
 
type CreateUserPlanAssignmentsFormikProps = FormikFormProps<CreateUserPlanAssignmentsFormValues, PlanAssignment[]>;
 
const initialValues = {
  planIds: [],
};
 
export type CreateUserPlanAssignmentsFormProps = Omit<
  CreateUserPlanAssignmentsFormikProps,
  'enableReinitialize' | 'initialValues' | 'onSubmit' | 'validationSchema'
> & {
  readonly userId: UserContract['id'];
};
 
export const CreateUserPlanAssignmentsForm = memo(function CreateUserPlanAssignmentsForm({
  userId,
  children,
  ...props
}: CreateUserPlanAssignmentsFormProps) {
  const { mutateAsync: upsertPlanAssignments } = useUpsertPlanAssignments();
  const { formatMessage } = useIntl();
 
  const validationSchema = useMemo(
    () =>
      z.strictObject({
        planIds: z.array(z.uuid()).min(1, {
          error: ({ minimum }) => ({
            message: formatMessage(
              { defaultMessage: 'Please select at least {min, plural, one {# plan} other {# plans}}.' },
              { min: minimum as number },
            ),
          }),
        }),
      }),
    [formatMessage],
  );
 
  const handleSubmit: CreateUserPlanAssignmentsFormikProps['onSubmit'] = useCallback(
    ({ planIds }) =>
      upsertPlanAssignments(
        planIds.map((planId) => ({
          planId,
          userId,
          // Can't know the main team since each user might not be on the same teams.
          mainTeamId: null,
          effectiveAsOf: null,
          effectiveUntil: null,
        })),
      ),
    [upsertPlanAssignments, userId],
  );
 
  return (
    <FormikForm
      {...props}
      enableReinitialize={false}
      initialValues={initialValues}
      validationSchema={validationSchema}
      onSubmit={handleSubmit}
    >
      {children}
    </FormikForm>
  );
});