Untitled

 avatar
unknown
plain_text
2 months ago
5.4 kB
2
Indexable
import React, { useEffect, useState } from "react";
import { useMutation, useQuery } from "@apollo/client";
import {
  Box,
  Button,
  TextField,
  Modal,
} from "@mui/material";
import Autocomplete from "react-autocomplete";

import { gql } from "../../__generated__";
import { CategoryTypesEnum } from "../../__generated__/graphql";
import { useAlert } from "../atoms/alertContext";
import { Category } from "../pages/master_data_request/categories_page";

// GraphQL Fragments
const COUNTRY_FRAGMENT = gql`
  fragment CountryFragment on Country {
    id
    name
  }
`;

const REGION_COUNTRY_QUERY = gql`
  query regionCountry_Query {
    whoami {
      id
      userCountries {
        country {
          ...CountryFragment
        }
      }
      regionUsers {
        region {
          regionCountries {
            country {
              ...CountryFragment
            }
          }
        }
      }
    }
  }
  ${COUNTRY_FRAGMENT}
`;

// Mutations
const ADD_CATEGORY_MUTATION = gql`
  mutation addCategory($input: CreateCategoryInput!) {
    createCategory(input: $input) {
      success
      message
    }
  }
`;

const UPDATE_CATEGORY_MUTATION = gql`
  mutation updateCategory($input: [UpdateCategoryOrTopicInput!]!) {
    updateCategoryOrTopic(input: $input) {
      success
      message
    }
  }
`;

// Props Interface
interface CategoryModalProps {
  open: boolean;
  onClose: () => void;
  modalData?: Category | null;
}

const CategoryModal: React.FC<CategoryModalProps> = ({ open, onClose, modalData }) => {
  const [categoryName, setCategoryName] = useState("");
  const [selectedCountries, setSelectedCountries] = useState<{ id: number; name: string }[]>([]);
  const [searchTerm, setSearchTerm] = useState("");

  const { showAlert } = useAlert();
  const { data } = useQuery(REGION_COUNTRY_QUERY);
  const [addCategory] = useMutation(ADD_CATEGORY_MUTATION);
  const [updateCategory] = useMutation(UPDATE_CATEGORY_MUTATION);

  useEffect(() => {
    if (modalData) {
      setCategoryName(modalData.name);
      setSelectedCountries(modalData.groupCountries.map(gc => ({ id: gc.country.id, name: gc.country.name })));
    } else {
      setCategoryName("");
      setSelectedCountries([]);
    }
  }, [modalData]);

  const allCountries = data?.whoami?.userCountries.map((uc: any) => uc.country) || [];

  const handleSubmit = async () => {
    const input = {
      name: categoryName,
      countryId: selectedCountries.map(c => c.id),
      type: CategoryTypesEnum.Category,
    };

    try {
      if (modalData) {
        const response = await updateCategory({ variables: { input: [{ ...input, groupId: parseInt(modalData.id) }] } });
        if (response?.data.updateCategoryOrTopic.success) {
          showAlert("Category updated successfully!", "success");
        } else {
          showAlert(response?.data.updateCategoryOrTopic.message, "error");
        }
      } else {
        const response = await addCategory({ variables: { input } });
        if (response?.data.createCategory.success) {
          showAlert("Category added successfully!", "success");
        } else {
          showAlert(response?.data.createCategory.message, "error");
        }
      }
      onClose();
    } catch {
      showAlert("Error occurred. Please try again.", "error");
    }
  };

  return (
    <Modal open={open} onClose={onClose}>
      <Box
        sx={{
          position: "absolute",
          top: "50%",
          left: "50%",
          transform: "translate(-50%, -50%)",
          width: 600,
          bgcolor: "background.paper",
          boxShadow: 24,
          p: 4,
          borderRadius: 2,
        }}
      >
        <h2>{modalData ? "Edit Category" : "Add Category"}</h2>
        <TextField
          label="Category Name"
          fullWidth
          value={categoryName}
          onChange={e => setCategoryName(e.target.value)}
          variant="outlined"
          sx={{ mb: 2 }}
        />
        <Autocomplete
          getItemValue={item => item.name}
          items={allCountries}
          renderItem={(item, isHighlighted) => (
            <div key={item.id} style={{ background: isHighlighted ? "#ddd" : "#fff", padding: "5px" }}>
              {item.name}
            </div>
          )}
          value={searchTerm}
          onChange={e => setSearchTerm(e.target.value)}
          onSelect={(val, item) => {
            if (!selectedCountries.find(c => c.id === item.id)) {
              setSelectedCountries([...selectedCountries, item]);
            }
            setSearchTerm("");
          }}
        />
        <Box sx={{ mt: 2 }}>
          {selectedCountries.map(country => (
            <Button
              key={country.id}
              sx={{ mr: 1, mb: 1 }}
              variant="outlined"
              onClick={() => setSelectedCountries(selectedCountries.filter(c => c.id !== country.id))}
            >
              {country.name} ×
            </Button>
          ))}
        </Box>
        <Box sx={{ display: "flex", justifyContent: "flex-end", mt: 2, gap: 1 }}>
          <Button variant="contained" onClick={handleSubmit}>
            {modalData ? "Update" : "Add"}
          </Button>
          <Button variant="outlined" onClick={onClose}>
            Cancel
          </Button>
        </Box>
      </Box>
    </Modal>
  );
};

export default CategoryModal;
Editor is loading...
Leave a Comment