-
{ `${modaldata?.modalType} `}
-
-
+
{`${modaldata?.modalType} `}
+
+
{modaldata.modalType === "Application Role" && (
-
+
)}
{modaldata.modalType === "Edit-Application Role" && (
@@ -122,7 +147,10 @@ const MasterModal = ({ modaldata, closeModal }) => {
)}
{modaldata.modalType === "Edit-Activity" && (
-
+
)}
{modaldata.modalType === "Work Category" && (
@@ -133,10 +161,10 @@ const MasterModal = ({ modaldata, closeModal }) => {
{modaldata.modalType === "Contact Category" && (
)}
- {modaldata.modalType === "Edit-Contact Category" && (
+ {modaldata.modalType === "Edit-Contact Category" && (
)}
- {modaldata.modalType === "Contact Tag" && (
+ {modaldata.modalType === "Contact Tag" && (
)}
{modaldata.modalType === "Edit-Contact Tag" && (
diff --git a/src/hooks/masterHook/useMaster.js b/src/hooks/masterHook/useMaster.js
index a5c43a51..20caff62 100644
--- a/src/hooks/masterHook/useMaster.js
+++ b/src/hooks/masterHook/useMaster.js
@@ -1,7 +1,9 @@
-import {useState,useEffect} from "react"
+import {useState,useEffect, useCallback} from "react"
import { MasterRespository } from "../../repositories/MastersRepository";
import { cacheData,getCachedData } from "../../slices/apiDataManager";
import { useSelector } from "react-redux";
+import {useMutation, useQueries, useQuery, useQueryClient} from "@tanstack/react-query";
+import showToast from "../../services/toastService";
@@ -9,214 +11,687 @@ import { useSelector } from "react-redux";
-export const useFeatures = () =>
- useMasterData("masterFeatures", MasterRespository.getFeatures);
-export const useMasterRole = () =>
- useMasterData("masterRole", MasterRespository.getRoles);
+// const useMaster = () => {
-
-const useMaster = (isMa) => {
-
- const selectedMaster = useSelector((store)=>store.localVariables.selectedMaster);
- const [data, setData] = useState([]);
- const [loading, setLoading] = useState(true);
- const [error, setError] = useState("");
- useEffect(() => {
- const fetchData = async () => {
- if (!selectedMaster) return;
- setLoading(true);
- try {
- const cachedData = getCachedData(selectedMaster);
- if (cachedData) {
+// const selectedMaster = useSelector((store)=>store.localVariables.selectedMaster);
+// const [data, setData] = useState([]);
+// const [loading, setLoading] = useState(true);
+// const [error, setError] = useState("");
+// useEffect(() => {
+// const fetchData = async () => {
+// if (!selectedMaster) return;
+// setLoading(true);
+// try {
+// const cachedData = getCachedData(selectedMaster);
+// if (cachedData) {
- setData(cachedData);
+// setData(cachedData);
- } else {
- let response;
- switch (selectedMaster) {
- case "Application Role":
- response = await MasterRespository.getRoles();
- response = response.data;
- break;
- case "Job Role":
- response = await MasterRespository.getJobRole();
- response = response.data
- break;
- case "Activity":
- response = await MasterRespository.getActivites();
- response = response.data
- break;
- case "Work Category":
- response = await MasterRespository.getWorkCategory();
- response = response.data
- break;
- case "Contact Category":
- response = await MasterRespository.getContactCategory();
- response = response.data
- break;
- case "Contact Tag":
- response = await MasterRespository.getContactTag();
- response = response.data
- break;
- case "Status":
- response = [{description: null,featurePermission: null,id: "02dd4761-363c-49ed-8851-3d2489a3e98d",status:"status 1"},{description: null,featurePermission: null,id: "03dy9761-363c-49ed-8851-3d2489a3e98d",status:"status 2"},{description: null,featurePermission: null,id: "03dy7761-263c-49ed-8851-3d2489a3e98d",status:"Status 3"}];
- break;
- default:
- response = [];
- }
+// } else {
+// let response;
+// switch (selectedMaster) {
+// case "Application Role":
+// response = await MasterRespository.getRoles();
+// response = response.data;
+// break;
+// case "Job Role":
+// response = await MasterRespository.getJobRole();
+// response = response.data
+// break;
+// case "Activity":
+// response = await MasterRespository.getActivites();
+// response = response.data
+// break;
+// case "Work Category":
+// response = await MasterRespository.getWorkCategory();
+// response = response.data
+// break;
+// case "Contact Category":
+// response = await MasterRespository.getContactCategory();
+// response = response.data
+// break;
+// case "Contact Tag":
+// response = await MasterRespository.getContactTag();
+// response = response.data
+// break;
+// case "Status":
+// response = [{description: null,featurePermission: null,id: "02dd4761-363c-49ed-8851-3d2489a3e98d",status:"status 1"},{description: null,featurePermission: null,id: "03dy9761-363c-49ed-8851-3d2489a3e98d",status:"status 2"},{description: null,featurePermission: null,id: "03dy7761-263c-49ed-8851-3d2489a3e98d",status:"Status 3"}];
+// break;
+// default:
+// response = [];
+// }
- if (response) {
- setData(response);
- cacheData(selectedMaster, response);
- }
- }
- } catch (err) {
- setError("Failed to fetch data.");
- } finally {
- setLoading(false);
- }
- };
+// if (response) {
+// setData(response);
+// cacheData(selectedMaster, response);
+// }
+// }
+// } catch (err) {
+// setError("Failed to fetch data.");
+// } finally {
+// setLoading(false);
+// }
+// };
- if ( selectedMaster )
- {
+// if ( selectedMaster )
+// {
- fetchData();
- }
+// fetchData();
+// }
- }, [selectedMaster]);
+// }, [selectedMaster]);
- return { data, loading, error }
+// return { data, loading, error }
+// };
+
+
+
+
+// export const useActivitiesMaster = () =>
+// {
+// const [ activities, setActivites ] = useState( [] )
+// const [ loading, setloading ] = useState( false );
+// const [ error, setError ] = useState()
+// const fetchActivities =async () => {
+// setloading(true);
+// try {
+// const response = await MasterRespository.getActivites();
+// setActivites(response.data);
+// cacheData( "ActivityMaster", response.data );
+// setloading(false);
+// } catch (err) {
+// setError(err);
+// setloading(false);
+// }
+// }
+// useEffect( () =>
+// {
+// const cacheddata = getCachedData( "ActivityMaster" );
+// if ( !cacheddata )
+// {
+// fetchActivities()
+// } else
+// {
+// setActivites(cacheddata);
+// }
+// }, [] )
+
+// return {activities,loading,error}
+// }
+
+// export const useWorkCategoriesMaster = () =>
+// {
+// const [ categories, setCategories ] = useState( [] )
+// const [ categoryLoading, setloading ] = useState( false );
+// const [ categoryError, setError ] = useState( "" )
+
+// const fetchCategories =async () => {
+// const cacheddata = getCachedData("Work Category");
+
+// if (!cacheddata) {
+// setloading(true);
+// try {
+// const response = await MasterRespository.getWorkCategory();
+// setCategories(response.data);
+// cacheData("Work Category", response.data);
+// } catch (err) {
+// setError(err);
+// console.log(err);
+// } finally {
+// setloading(false);
+// }
+// } else {
+// setCategories(cacheddata);
+// }
+// }
+// useEffect( () =>
+// {
+// fetchCategories()
+// }, [] )
+
+// return {categories,categoryLoading,categoryError}
+// }
+
+// export const useContactCategory = () =>
+// {
+// const [ contactCategory, setContactCategory ] = useState( [] )
+// const [ loading, setLoading ] = useState( false )
+// const [ Error, setError ] = useState()
+
+// const fetchConatctCategory = async() =>
+// {
+// const cache_Category = getCachedData( "Contact Category" );
+// if ( !cache_Category )
+// {
+// try
+// {
+// let resp = await MasterRespository.getContactCategory();
+// setContactCategory( resp.data );
+// cacheData("Contact Category",resp.data)
+// } catch ( error )
+// {
+// setError(error)
+// }
+// } else
+// {
+// setContactCategory(cache_Category)
+// }
+// }
+
+// useEffect( () =>
+// {
+// fetchConatctCategory()
+// }, [] )
+// return { contactCategory,loading,Error}
+// }
+// export const useContactTags = () => {
+// const [contactTags, setContactTags] = useState([]);
+// const [loading, setLoading] = useState(false);
+// const [error, setError] = useState(null);
+
+// useEffect(() => {
+// const fetchContactTag = async () => {
+// const cache_Tags = getCachedData("Contact Tag");
+
+// if (!cache_Tags) {
+// setLoading(true);
+// try {
+// const resp = await MasterRespository.getContactTag();
+// setContactTags(resp.data);
+// cacheData("Contact Tag", resp.data);
+// } catch (err) {
+// setError(err);
+// } finally {
+// setLoading(false);
+// }
+// } else {
+// setContactTags(cache_Tags);
+// }
+// };
+
+// fetchContactTag();
+// }, []);
+
+// return { contactTags, loading, error };
+// };
+
+// Separate matser-------------
+
+export const useActivitiesMaster = () =>
+{
+ const { data:activities=[],isLoading:loading,error} = useQuery( {
+ queryKey: [ "ActivityMaster" ],
+ queryFn: async() =>
+ {
+ const response = await MasterRespository.getActivites();
+ return response.data
+ },
+ onError: (error) => {
+ showToast(error?.response?.data?.message || error.message || "Failed to fetch ActivityMasters", "error");
+ },
+ } )
+ return {activities,loading,error}
+}
+export const useWorkCategoriesMaster = () => {
+ const {
+ data: categories = [],
+ isLoading: categoryLoading,
+ error: categoryError,
+ } = useQuery({
+ queryKey: ["Work Category"],
+ queryFn: async () => {
+ const response = await MasterRespository.getWorkCategory();
+ return response.data;
+ },
+ onError: (error) => {
+ showToast(
+ error?.response?.data?.message ||
+ error.message ||
+ "Failed to fetch work categories",
+ "error"
+ );
+ },
+ });
+
+ return { categories, categoryLoading, categoryError };
+};
+
+
+export const useContactCategory = () =>
+{
+ const {data:contactCategory=[],isLoading:loading,error:Error } = useQuery( {
+ queryKey: [ "Contact Category" ],
+ queryFn: async () =>
+ {
+ let resp = await MasterRespository.getContactCategory();
+ return resp.data
+ },
+ onError: (error) => {
+ showToast(error?.response?.data?.message || error.message || "Failed to fetch Contact categories", "error");
+ },
+ } )
+ return { contactCategory,loading,Error}
+}
+
+export const useContactTags = () => {
+ const {
+ data: contactTags = [],
+ isLoading: loading,
+ error,
+ } = useQuery({
+ queryKey: ["Contact Tag"],
+ queryFn: async () => {
+ const res = await MasterRespository.getContactTag();
+ return res.data;
+ },
+ onError: (error) => {
+ showToast(
+ error?.response?.data?.message ||
+ error.message ||
+ "Failed to fetch Contact Tag",
+ "error"
+ );
+ },
+ });
+
+ return { contactTags, loading, error };
+};
+
+// ===Application Masters Query=================================================
+
+const fetchMasterData = async (masterType) => {
+ switch (masterType) {
+ case "Application Role":
+ return (await MasterRespository.getRoles()).data;
+ case "Job Role":
+ return (await MasterRespository.getJobRole()).data;
+ case "Activity":
+ return (await MasterRespository.getActivites()).data;
+ case "Work Category":
+ return (await MasterRespository.getWorkCategory()).data;
+ case "Contact Category":
+ return (await MasterRespository.getContactCategory()).data;
+ case "Contact Tag":
+ return (await MasterRespository.getContactTag()).data;
+ case "Status":
+ return [
+ {
+ description: null,
+ featurePermission: null,
+ id: "02dd4761-363c-49ed-8851-3d2489a3e98d",
+ status: "status 1",
+ },
+ {
+ description: null,
+ featurePermission: null,
+ id: "03dy9761-363c-49ed-8851-3d2489a3e98d",
+ status: "status 2",
+ },
+ {
+ description: null,
+ featurePermission: null,
+ id: "03dy7761-263c-49ed-8851-3d2489a3e98d",
+ status: "Status 3",
+ },
+ ];
+ default:
+ return [];
+ }
+};
+
+const useMaster = () => {
+ const selectedMaster = useSelector((store) => store.localVariables.selectedMaster);
+ const queryFn = useCallback(() => fetchMasterData(selectedMaster), [selectedMaster]);
+ const {
+ data = [],
+ isLoading,
+ error,
+ } = useQuery({
+ queryKey: ["masterData", selectedMaster],
+ queryFn,
+ enabled: !!selectedMaster,
+ staleTime: 1000 * 60 * 10,
+ refetchOnWindowFocus: false,
+ onError: (error) => {
+ showToast(error?.response?.data?.message || error.message || `Failed to fetch ${selectedMaster} Maseter`, "error");
+ },
+ });
+
+ return { data, loading: isLoading, error };
};
export default useMaster;
-export const useActivitiesMaster = () =>
- {
- const [ activities, setActivites ] = useState( [] )
- const [ loading, setloading ] = useState( false );
- const [ error, setError ] = useState()
- const fetchActivities =async () => {
- setloading(true);
- try {
- const response = await MasterRespository.getActivites();
- setActivites(response.data);
- cacheData( "ActivityMaster", response.data );
- setloading(false);
- } catch (err) {
- setError(err);
- setloading(false);
- }
- }
- useEffect( () =>
- {
- const cacheddata = getCachedData( "ActivityMaster" );
- if ( !cacheddata )
- {
- fetchActivities()
- } else
- {
- setActivites(cacheddata);
- }
- }, [] )
-
- return {activities,loading,error}
- }
+// ================================Mutation====================================
- export const useWorkCategoriesMaster = () =>
- {
- const [ categories, setCategories ] = useState( [] )
- const [ categoryLoading, setloading ] = useState( false );
- const [ categoryError, setError ] = useState( "" )
-
- const fetchCategories =async () => {
- const cacheddata = getCachedData("Work Category");
-
- if (!cacheddata) {
- setloading(true);
- try {
- const response = await MasterRespository.getWorkCategory();
- setCategories(response.data);
- cacheData("Work Category", response.data);
- } catch (err) {
- setError(err);
- console.log(err);
- } finally {
- setloading(false);
- }
- } else {
- setCategories(cacheddata);
- }
- }
- useEffect( () =>
- {
- fetchCategories()
- }, [] )
-
- return {categories,categoryLoading,categoryError}
-}
-
-export const useContactCategory = () =>
+// Job Role-----------------------------------
+export const useUpdateJobRole = (onSuccessCallback, onErrorCallback) => {
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: async ({ id, payload }) => {
+ const response = await MasterRespository.updateJobRole(id, payload);
+ return response.data;
+ },
+ onSuccess: (data, variables) => {
+ showToast("JobRole updated successfully.", "success");
+
+ queryClient.invalidateQueries({
+ queryKey: ["masterData", "Job Role"],
+ });
+
+ if (onSuccessCallback) onSuccessCallback(data);
+ },
+ onError: (error) => {
+ showToast(error.message || "Something went wrong", "error");
+ if (onErrorCallback) onErrorCallback(error);
+ },
+ });
+};
+
+export const useCreateJobRole = (onSuccessCallback) => {
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: async (payload) => {
+ const response = await MasterRespository.createJobRole(payload);
+ return response.data;
+ },
+ onSuccess: (data) => {
+ showToast("JobRole added successfully.", "success");
+
+ queryClient.invalidateQueries({queryKey:["masterData", "Job Role"]});
+
+ if (onSuccessCallback) onSuccessCallback(data);
+ },
+ onError: (error) => {
+ showToast(error.message || "Something went wrong", "error");
+ },
+ });
+};
+
+// Application Role-------------------------------------------
+
+export const useCreateApplicationRole = (onSuccessCallback) =>
{
- const [ contactCategory, setContactCategory ] = useState( [] )
- const [ loading, setLoading ] = useState( false )
- const [ Error, setError ] = useState()
-
- const fetchConatctCategory = async() =>
- {
- const cache_Category = getCachedData( "Contact Category" );
- if ( !cache_Category )
+ const queryClient = useQueryClient();
+
+ return useMutation( {
+ mutationFn: async ( payload ) =>
{
- try
- {
- let resp = await MasterRespository.getContactCategory();
- setContactCategory( resp.data );
- cacheData("Contact Category",resp.data)
- } catch ( error )
- {
- setError(error)
- }
- } else
+ const resp = await MasterRespository.createRole( payload );
+ return resp.data;
+ },
+ onSuccess: ( data ) =>
{
- setContactCategory(cache_Category)
+ queryClient.invalidateQueries( {queryKey:[ "masterData", "Application Role" ]} )
+ showToast( "Application Role added successfully", "success" );
+ if(onSuccessCallback) onSuccessCallback(data)
+ },
+ onError: ( error ) =>
+ {
+ showToast(error.message || "Something went wrong", "error");
}
- }
-
- useEffect( () =>
- {
- fetchConatctCategory()
- }, [] )
- return { contactCategory,loading,Error}
+ })
}
-export const useContactTags = () => {
- const [contactTags, setContactTags] = useState([]);
- const [loading, setLoading] = useState(false);
- const [error, setError] = useState(null);
- useEffect(() => {
- const fetchContactTag = async () => {
- const cache_Tags = getCachedData("Contact Tag");
+export const useUpdateApplicationRole = (onSuccessCallback) =>
+{
+ const queryClient = useQueryClient();
- if (!cache_Tags) {
- setLoading(true);
- try {
- const resp = await MasterRespository.getContactTag();
- setContactTags(resp.data);
- cacheData("Contact Tag", resp.data);
- } catch (err) {
- setError(err);
- } finally {
- setLoading(false);
- }
- } else {
- setContactTags(cache_Tags);
+ return useMutation({
+ mutationFn: async ( {id, payload} ) =>
+ {
+ const response = await MasterRespository.updateRoles(id,payload);
+ return response.data;
+ },
+ onSuccess: (data, variables) => {
+
+ queryClient.invalidateQueries({
+ queryKey: ["masterData", "Application Role"],
+ });
+ showToast("Application Role updated successfully.", "success");
+
+ if (onSuccessCallback) onSuccessCallback(data);
+ },
+ onError: (error) => {
+ showToast(error.message || "Something went wrong", "error");
+ },
+ });
+}
+
+// Activity------------------------------
+export const useCreateActivity = (onSuccessCallback) =>
+{
+ const queryClient = useQueryClient();
+
+ return useMutation( {
+ mutationFn: async ( payload ) =>
+ {
+ const resp = await MasterRespository.createActivity(payload);
+ return resp.data;
+ },
+ onSuccess: ( data ) =>
+ {
+ queryClient.invalidateQueries( {queryKey:[ "masterData", "Activity" ]} )
+ showToast( "Activity added successfully", "success" );
+ if(onSuccessCallback) onSuccessCallback(data)
+ },
+ onError: ( error ) =>
+ {
+ showToast(error.message || "Something went wrong", "error");
+ }
+ })
+}
+
+export const useUpdateActivity = (onSuccessCallback) =>
+{
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: async ( {id, payload} ) =>
+ {
+ const response = await MasterRespository.updateActivity(id,payload);
+ return response.data;
+ },
+ onSuccess: (data, variables) => {
+
+ queryClient.invalidateQueries({
+ queryKey: ["masterData", "Activity"],
+ });
+ showToast("Activity updated successfully.", "success");
+
+ if (onSuccessCallback) onSuccessCallback(data);
+ },
+ onError: (error) => {
+ showToast(error.message || "Something went wrong", "error");
+ },
+ });
+}
+
+
+//-----Create work Category-------------------------------
+export const useCreateWorkCategory = (onSuccessCallback) =>
+{
+ const queryClient = useQueryClient();
+
+ return useMutation( {
+ mutationFn: async ( payload ) =>
+ {
+ const resp = await MasterRespository.createWorkCategory(payload);
+ return resp.data;
+ },
+ onSuccess: ( data ) =>
+ {
+ queryClient.invalidateQueries({queryKey: [ "masterData", "Work Category" ]} )
+ showToast( "Work Category added successfully", "success" );
+ if(onSuccessCallback) onSuccessCallback(data)
+ },
+ onError: ( error ) =>
+ {
+ showToast(error.message || "Something went wrong", "error");
+ }
+ })
+}
+
+export const useUpdateWorkCategory = (onSuccessCallback) =>
+{
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: async ( {id, payload} ) =>
+ {
+ const response = await MasterRespository.updateWorkCategory(id,payload);
+ return response.data;
+ },
+ onSuccess: (data, variables) => {
+
+ queryClient.invalidateQueries({
+ queryKey: ["masterData", "Work Category"],
+ });
+ showToast("Work Category updated successfully.", "success");
+
+ if (onSuccessCallback) onSuccessCallback(data);
+ },
+ onError: (error) => {
+ showToast(error.message || "Something went wrong", "error");
+ },
+ });
+}
+
+//-- Contact Category---------------------------
+
+
+export const useCreateContactCategory = (onSuccessCallback) =>
+{
+ const queryClient = useQueryClient();
+
+ return useMutation( {
+ mutationFn: async ( payload ) =>
+ {
+ const resp = await MasterRespository.createContactCategory(payload);
+ return resp.data;
+ },
+ onSuccess: ( data ) =>
+ {
+ queryClient.invalidateQueries( {queryKey:[ "masterData", "Contact Category" ]} )
+ showToast( "Contact Category added successfully", "success" );
+ if(onSuccessCallback) onSuccessCallback(data)
+ },
+ onError: ( error ) =>
+ {
+ showToast(error.message || "Something went wrong", "error");
+ }
+ })
+}
+
+
+export const useUpdateContactCategory = (onSuccessCallback) =>
+{
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: async ( {id, payload} ) =>
+ {
+ const response = await MasterRespository.updateContactCategory(id,payload);
+ return response.data;
+ },
+ onSuccess: (data, variables) => {
+
+ queryClient.invalidateQueries({
+ queryKey: ["masterData", "Contact Category"],
+ });
+ showToast("Contact Category updated successfully.", "success");
+
+ if (onSuccessCallback) onSuccessCallback(data);
+ },
+ onError: (error) => {
+ showToast(error.message || "Something went wrong", "error");
+ },
+ });
+}
+
+// ---------Contact Tag-------------------
+
+export const useCreateContactTag = (onSuccessCallback) =>
+{
+ const queryClient = useQueryClient();
+
+ return useMutation( {
+ mutationFn: async ( payload ) =>
+ {
+ const resp = await MasterRespository.createContactTag(payload);
+ return resp.data;
+ },
+ onSuccess: ( data ) =>
+ {
+ queryClient.invalidateQueries( {queryKey:[ "masterData", "Contact Tag" ]} )
+ showToast( "Contact Tag added successfully", "success" );
+ if(onSuccessCallback) onSuccessCallback(data)
+ },
+ onError: ( error ) =>
+ {
+ showToast(error.message || "Something went wrong", "error");
+ }
+ })
+}
+
+
+export const useUpdateContactTag = (onSuccessCallback) =>
+{
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: async ( {id, payload} ) =>
+ {
+ debugger
+ const response = await MasterRespository.updateContactTag(id,payload);
+ return response.data;
+ },
+ onSuccess: (data, variables) => {
+
+ queryClient.invalidateQueries({
+ queryKey: ["masterData", "Contact Tag"],
+ });
+ showToast("Contact Tag updated successfully.", "success");
+
+ if (onSuccessCallback) onSuccessCallback(data);
+ },
+ onError: (error) => {
+ showToast(error.message || "Something went wrong", "error");
+ },
+ });
+}
+
+// -Delete Master --------
+export const useDeleteMasterItem = () => {
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: async ( {masterType, item} ) =>
+ {
+ const deleteFn = MasterRespository[masterType];
+ if (!deleteFn) {
+ throw new Error(`No delete strategy defined for master type: ${masterType}`);
}
- };
- fetchContactTag();
- }, []);
+ await deleteFn(item.id);
+ return { masterType };
+ },
- return { contactTags, loading, error };
+ onSuccess: ({ masterType }) => {
+ queryClient.invalidateQueries({ queryKey: ["masterData", masterType] });
+
+ showToast(`${masterType} deleted successfully.`, "success");
+ },
+
+ onError: (error) => {
+ const message =
+ error?.response?.data?.message || error?.message || "Error occurred during deletion";
+ showToast(message, "error");
+ },
+ });
};
\ No newline at end of file
diff --git a/src/hooks/useEmployees.js b/src/hooks/useEmployees.js
index 67c9f6b8..4839d36c 100644
--- a/src/hooks/useEmployees.js
+++ b/src/hooks/useEmployees.js
@@ -3,236 +3,274 @@ import { cacheData, getCachedData } from "../slices/apiDataManager";
import { RolesRepository } from "../repositories/MastersRepository";
import EmployeeRepository from "../repositories/EmployeeRepository";
import ProjectRepository from "../repositories/ProjectRepository";
+import { useMutation, useQuery, useQueryClient } from '@tanstack/react-query';
+import showToast from "../services/toastService";
+import {useSelector} from "react-redux";
+import {store} from "../store/store";
+import {queryClient} from "../layouts/AuthLayout";
-export const useAllEmployees = (showInactive) => {
- const [employeesList, setEmployeeList] = useState([]);
- const [loading, setLoading] = useState(false);
- const [error, setError] = useState();
- const fetchData = async () => {
- try {
- let EmployeeList_cached = getCachedData("AllEmployees");
- if (!EmployeeList_cached) {
- setLoading(true);
- const response = await EmployeeRepository.getAllEmployeeList(showInactive);
- cacheData("AllEmployees", response.data);
- setEmployeeList(response.data);
- setLoading(false);
- } else {
- setEmployeeList(EmployeeList_cached);
- setLoading(false);
- }
- } catch (error) {
- setError("Failed to fetch data.");
- setLoading(false);
- }
+
+
+// Query ---------------------------------------------------------------------------
+
+
+export const useAllEmployees = ( showInactive ) =>
+{
+ const {
+ data = [],
+ isLoading,
+ error,
+ refetch, // optional if you want recall functionality
+ } = useQuery({
+ queryKey: ['allEmployee', showInactive],
+ queryFn: async () => {
+ const res = await EmployeeRepository.getAllEmployeeList(showInactive);
+ return res.data;
+ },
+ });
+
+ return {
+ employeesList: data,
+ loading: isLoading,
+ error,
+ recallEmployeeData: refetch,
};
-
- useEffect(() => {
- fetchData();
- }, []);
- return { employeesList, loading, error };
};
-export const useEmployees = (selectedProject) => {
- const [employees, setEmployeeList] = useState([]);
- const [loading, setLoading] = useState(true);
- const [projects, setProjects] = useState([]);
+// ManageBucket.jsx
+export const useEmployees = ( selectedProject ) =>
+{
- const fetchData = async (projectid) => {
- try {
- let EmployeeByProject_Cache = getCachedData("employeeListByProject");
- if (
- !EmployeeByProject_Cache ||
- !EmployeeByProject_Cache.projectId === projectid
- ) {
- EmployeeRepository.getEmployeeListByproject(projectid)
- .then((response) => {
- setEmployeeList(response);
- cacheData("employeeListByProject", {
- data: response,
- projectId: projectid,
- });
- })
- .catch((error) => {
- setError("Failed to fetch data.");
- });
- } else {
- setEmployeeList(EmployeeByProject_Cache.data);
- }
- setLoading(false);
- } catch (err) {
- setError("Failed to fetch data.");
- setLoading(false);
- }
+ const {
+ data = [],
+ isLoading,
+ error,
+ refetch,
+ } = useQuery({
+ queryKey: ["employeeListByProject", selectedProject],
+ queryFn: async () => {
+ const res = await EmployeeRepository.getEmployeeListByproject(selectedProject);
+ return res.data || res;
+ },
+ enabled: !!selectedProject,
+ });
+
+ return {
+ employees: data,
+ loading: isLoading,
+ projects: [], // if needed, pass this separately or manage from another hook
+ reCallAllEmployee: refetch,
+ error,
};
-
- useEffect(() => {
- if (selectedProject) {
- fetchData(selectedProject);
- }
- }, [selectedProject]);
-
- return { employees, loading, projects, reCallAllEmployee };
};
+// ManageRole.jsx
export const useEmployeeRoles = (employeeId) => {
- const [loading, setLoading] = useState(true);
- const [error, setError] = useState();
- const [employeeRoles, setEmployeeRoles] = useState([]);
- const fetchData = async (employeeid) => {
- try {
- let response = await RolesRepository.getEmployeeRoles(employeeid);
- setEmployeeRoles(response.data);
- cacheData("employeelist", response.data);
- } catch (err) {
- setError("Failed to fetch data.");
- setEmployeeRoles([]);
- } finally {
- setLoading(false);
- }
+ const {
+ data = [],
+ isLoading: loading,
+ error,
+ } = useQuery({
+ queryKey: ['employeeRoles', employeeId],
+ queryFn: async () => {
+ const res = await RolesRepository.getEmployeeRoles(employeeId);
+ return res.data;
+ },
+ enabled: !!employeeId,
+ });
+
+ return {
+ employeeRoles: data,
+ loading,
+ error,
};
-
- useEffect(() => {
- if (employeeId) {
- fetchData(employeeId);
- }
- }, [employeeId]);
-
- return { employeeRoles, loading, error };
};
+// EmployeeProfile.jsx
export const useEmployeesByProject = (projectId) => {
- const [loading, setLoading] = useState(false);
- const [error, setError] = useState();
- const [employees, setEmployees] = useState([]);
+ const {
+ data = [],
+ isLoading: loading,
+ error,
+ refetch: recallProjectEmplloyee,
+ } = useQuery({
+ queryKey: ['projectEmployees', projectId],
+ queryFn: async () => {
+ const res = await ProjectRepository.getEmployeesByProject(projectId);
+ return res.data;
+ },
+ enabled: !!projectId,
+ });
- const fetchData = async () => {
- const Employees_cache = getCachedData("employeeListByProject");
- if (!Employees_cache || Employees_cache.projectId !== projectId) {
- setEmployees(true);
- ProjectRepository.getEmployeesByProject(projectId)
- .then((response) => {
- setEmployees(response.data);
- cacheData("employeeListByProject", {
- data: response.data,
- projectId,
- });
- setLoading(false);
- })
- .catch((error) => {
- setError("Failed to fetch data.");
- setLoading(false);
- });
- } else {
- setEmployees(Employees_cache.data);
- setLoading(false);
- }
+ return {
+ employees: data,
+ loading,
+ error,
+ recallProjectEmplloyee,
};
-
- useEffect(() => {
- fetchData(projectId);
- }, [projectId]);
-
- return { employees, loading, error, recallProjectEmplloyee: fetchData };
};
+// EmployeeList.jsx
export const useEmployeesAllOrByProjectId = (projectId, showInactive) => {
- const [employees, setEmployees] = useState([]);
- const [loading, setLoading] = useState(false);
- const [error, setError] = useState(null);
+ const isAllEmployees = !projectId && projectId !== undefined;
- const fetchData = async (showInactive) => {
- if ( projectId )
- {
- const Employees_cache = getCachedData("employeeListByProject");
- if (!Employees_cache || Employees_cache.projectId !== projectId) {
- setLoading(true);
- setError(null);
- try {
- const response = await ProjectRepository.getEmployeesByProject(
- projectId
- );
- setEmployees(response.data);
- cacheData("employeeListByProject", {
- data: response.data,
- projectId,
- });
- setLoading(false);
- } catch (err) {
- setError("Failed to fetch data.");
- setLoading(false);
- }
- } else {
- setEmployees(Employees_cache.data);
- setLoading(false);
- }
- } else
- {
- const cacheKey = showInactive
- ? "allInactiveEmployeeList"
- : "allEmployeeList";
+ const queryKey = isAllEmployees
+ ? ['allEmployees', showInactive]
+ : ['projectEmployees', projectId];
- try {
- const response = await EmployeeRepository.getAllEmployeeList(
- showInactive
- );
- setEmployees(response.data);
- cacheData(cacheKey, { data: response.data });
- setLoading(false);
- } catch (err) {
- setError("Failed to fetch data.");
- setLoading(false);
- }
-
+ const queryFn = async () => {
+ if (isAllEmployees) {
+ const res = await EmployeeRepository.getAllEmployeeList(showInactive);
+ return res.data;
+ } else {
+ const res = await ProjectRepository.getEmployeesByProject(projectId);
+ return res.data;
}
};
- useEffect(() => {
- fetchData(showInactive); // Fetch data when the component mounts or projectId changes
- }, [projectId]); // Re-fetch when projectId changes
+ const {
+ data: employees = [],
+ isLoading,
+ error,
+ refetch,
+ } = useQuery({
+ queryKey,
+ queryFn,
+ enabled: isAllEmployees || !!projectId,
+ });
return {
employees,
+ loading: isLoading,
+ error,
+ recallEmployeeData: refetch,
+ };
+};
+
+// ManageEmployee.jsx
+export const useEmployeeProfile = ( employeeId ) =>
+{
+ const isEnabled = !!employeeId;
+ const {
+ data = null,
+ isLoading: loading,
+ error,
+ refetch
+ } = useQuery({
+ queryKey: ['employeeProfile', employeeId],
+ queryFn: async () => {
+ if (!employeeId) return null;
+ const res = await EmployeeRepository.getEmployeeProfile(employeeId);
+ return res.data;
+ },
+ enabled: isEnabled,
+ });
+
+ return {
+ employee: data,
loading,
error,
- recallEmployeeData: fetchData,
+ refetch
};
};
-export const useEmployeeProfile = (employeeId) => {
- const [loading, setLoading] = useState(true);
- const [error, setError] = useState();
- const [employee, setEmployees] = useState(null);
- const fetchData = async () => {
- if (!employeeId) {
- // Reset the state if no employeeId (e.g., opening for 'add' mode)
- setEmployees(null);
- setLoading(false);
- return;
- }
- const Employee_cache = getCachedData("employeeProfile");
- if (!Employee_cache || Employee_cache.employeeId !== employeeId) {
- EmployeeRepository.getEmployeeProfile(employeeId)
- .then((response) => {
- setEmployees(response.data);
- cacheData("employeeProfile", { data: response.data, employeeId });
- setLoading(false);
- })
- .catch((error) => {
- setError("Failed to fetch data.");
- setLoading(false);
- });
- } else {
- setEmployees(Employee_cache.data);
- setLoading(false);
- }
- };
+// Mutation------------------------------------------------------------------
- useEffect(() => {
- fetchData();
- }, [employeeId]);
- return { employee, loading, error };
+
+export const useUpdateEmployee = () =>
+{
+ const selectedProject = useSelector((store)=>store.localVariables.projectId)
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: (employeeData) => EmployeeRepository.manageEmployee(employeeData),
+ onSuccess: (_, variables) => {
+ const id = variables.id || variables.employeeId;
+ const isAllEmployee = variables.IsAllEmployee;
+
+ // Cache invalidation
+ queryClient.invalidateQueries( {queryKey:[ 'allEmployees'] });
+ // queryClient.invalidateQueries(['employeeProfile', id]);
+ queryClient.invalidateQueries( {queryKey: [ 'projectEmployees' ]} );
+ queryClient.removeQueries( {queryKey: [ "empListByProjectAllocated" ]} );
+
+ // queryClient.invalidateQueries( {queryKey:[ 'employeeListByProject']} );
+ showToast( `Employee ${ id ? 'updated' : 'created' } successfully`, 'success' );
+ },
+ onError: (error) => {
+ const msg = error?.response?.data?.message || error.message || 'Something went wrong';
+ showToast(msg, 'error');
+ },
+ });
+};
+
+
+
+export const useSuspendEmployee = ({ setIsDeleteModalOpen, setemployeeLodaing }) => {
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: (id) => {
+ setemployeeLodaing(true);
+ return EmployeeRepository.deleteEmployee(id);
+ },
+
+ onSuccess: () => {
+ showToast("Employee deleted successfully.", "success");
+
+ // queryClient.invalidateQueries( ['allEmployee',false]);
+ queryClient.invalidateQueries( {queryKey: [ 'projectEmployees' ]} );
+ queryClient.invalidateQueries( {queryKey:[ 'employeeListByProject' ,selectedProject]} );
+
+ setIsDeleteModalOpen(false);
+ },
+
+ onError: (error) => {
+ const message =
+ error.response?.data?.message ||
+ error.message ||
+ "An unexpected error occurred";
+ showToast(message, "error");
+ setIsDeleteModalOpen(false);
+ },
+
+ onSettled: () => {
+ setemployeeLodaing(false);
+ },
+ });
+};
+
+// Manage Role
+
+
+export const useUpdateEmployeeRoles = ({ onClose, resetForm, onSuccessCallback } = {}) => {
+ const queryClient = useQueryClient();
+ const mutation = useMutation({
+ mutationFn: (updates) => RolesRepository.createEmployeeRoles(updates),
+ onSuccess: () => {
+ showToast("Roles updated successfully", "success");
+
+ resetForm?.();
+ onClose?.();
+ onSuccessCallback?.();
+
+ queryClient.invalidateQueries( {queryKey: [ "employeeRoles" ]} );
+ queryClient.invalidateQueries( {queryKey: [ "profile" ]} );
+ },
+ onError: (err) => {
+ const message =
+ err?.response?.data?.message || err?.message || "Error occurred while updating roles";
+ showToast(message, "error");
+ },
+ });
+
+ return {
+ updateRoles: mutation.mutate,
+ isPending: mutation.isPending,
+ isError: mutation.isError,
+ error: mutation.error,
+ };
};
diff --git a/src/hooks/useMasterRole.js b/src/hooks/useMasterRole.js
index d0d6cd47..68e94863 100644
--- a/src/hooks/useMasterRole.js
+++ b/src/hooks/useMasterRole.js
@@ -1,7 +1,7 @@
import { useEffect, useState } from "react";
import { cacheData,getCachedData } from "../slices/apiDataManager";
import { MasterRespository } from "../repositories/MastersRepository";
-
+import { useQuery } from "@tanstack/react-query";
export const useMasterRole =()=>{
@@ -43,40 +43,55 @@ export const useMasterRole =()=>{
return {masterRole,loading}
}
-export const useFeatures =()=> {
- const [masterFeatures, setMasterFeatures] = useState([]);
- const [loading, setLoading] = useState(true);
- const [error, setError] = useState("");
+// export const useFeatures =()=> {
+// const [masterFeatures, setMasterFeatures] = useState([]);
+// const [loading, setLoading] = useState(true);
+// const [error, setError] = useState("");
- const fetchData = async () => {
+// const fetchData = async () => {
- try {
- const features_cache = getCachedData("masterFeatures");
- if (!features_cache) {
- MasterRespository.getFeatures()
- .then((response) => {
- setMasterFeatures(response.data);
+// try {
+// const features_cache = getCachedData("masterFeatures");
+// if (!features_cache) {
+// MasterRespository.getFeatures()
+// .then((response) => {
+// setMasterFeatures(response.data);
- cacheData("features", response.data);
- setLoading(false)
- })
- .catch((error) => {
- setError("Failed to fetch data.");
- });
- }else{
- if (!masterFeatures.length) setMasterFeatures(features_cache);
- }
- } catch (err) {
- setError("Failed to fetch data.");
- } finally {
- setLoading(false);
- }
- };
+// cacheData("features", response.data);
+// setLoading(false)
+// })
+// .catch((error) => {
+// setError("Failed to fetch data.");
+// });
+// }else{
+// if (!masterFeatures.length) setMasterFeatures(features_cache);
+// }
+// } catch (err) {
+// setError("Failed to fetch data.");
+// } finally {
+// setLoading(false);
+// }
+// };
- useEffect(()=>{
- fetchData();
- },[])
+// useEffect(()=>{
+// fetchData();
+// },[])
- return{masterFeatures,loading}
-}
\ No newline at end of file
+// return{masterFeatures,loading}
+// }
+
+// -----------------Query- -------------------------
+export const useFeatures = () => {
+ const {data=[],isLoading,error} = useQuery({
+ queryKey: ["masterFeatures"],
+ queryFn: async () => {
+ const response = await MasterRespository.getFeatures();
+ return response.data;
+ },
+
+ } );
+ return {
+ masterFeatures:data,loading:isLoading,error
+ }
+};
\ No newline at end of file
diff --git a/src/hooks/usePagination.js b/src/hooks/usePagination.js
index b3e12b25..ffbbcf60 100644
--- a/src/hooks/usePagination.js
+++ b/src/hooks/usePagination.js
@@ -14,7 +14,7 @@ const usePagination = (data, itemsPerPage) => {
setCurrentPage(pageNumber);
};
- return { currentPage, totalPages, currentItems, paginate };
+ return { currentPage, totalPages, currentItems, paginate,setCurrentPage };
};
export default usePagination;
diff --git a/src/hooks/useProfile.js b/src/hooks/useProfile.js
index c8eeee8c..d9efefd1 100644
--- a/src/hooks/useProfile.js
+++ b/src/hooks/useProfile.js
@@ -3,60 +3,99 @@ import AuthRepository from "../repositories/AuthRepository";
import {cacheData, cacheProfileData, getCachedData, getCachedProfileData} from "../slices/apiDataManager";
import {useSelector} from "react-redux";
import eventBus from "../services/eventBus";
+import { useMutation, useQuery, useQueryClient } from '@tanstack/react-query';
let hasFetched = false;
let hasReceived = false;
-export const useProfile = () => {
- const loggedUser = useSelector( ( store ) => store.globalVariables.loginUser );
- const [profile, setProfile] = useState(null);
- const [loading, setLoading] = useState(false);
- const [error, setError] = useState("");
+// export const useProfile = () => {
+// const loggedUser = useSelector( ( store ) => store.globalVariables.loginUser );
+// const [profile, setProfile] = useState(null);
+// const [loading, setLoading] = useState(false);
+// const [error, setError] = useState("");
- const fetchData = async () => {
- try {
- setLoading(true);
- let response = await AuthRepository.profile();
- setProfile(response.data);
- cacheProfileData(response.data);
- } catch (error) {
- setError("Failed to fetch data.");
- } finally {
- setLoading(false);
- }
- };
+// const fetchData = async () => {
+// try {
+// setLoading(true);
+// let response = await AuthRepository.profile();
+// setProfile(response.data);
+// cacheProfileData(response.data);
+// } catch (error) {
+// setError("Failed to fetch data.");
+// } finally {
+// setLoading(false);
+// }
+// };
- const validation = () => {
- if (!hasFetched) {
- hasFetched = true;
- if (!loggedUser) {
- fetchData();
- } else {
- setProfile(loggedUser);
- }
- }
+// const validation = () => {
+// if (!hasFetched) {
+// hasFetched = true;
+// if (!loggedUser) {
+// fetchData();
+// } else {
+// setProfile(loggedUser);
+// }
+// }
- setProfile(loggedUser);
- }
+// setProfile(loggedUser);
+// }
- useEffect(() => {
- validation();
- }, [loggedUser]);
+// useEffect(() => {
+// validation();
+// }, [loggedUser]);
- const handler = useCallback(
- (data) => {
- if(!getCachedData("hasReceived")){
- cacheData("hasReceived", true);
- hasFetched = false;
- validation();
- }
- },[]
- );
+// const handler = useCallback(
+// (data) => {
+// if(!getCachedData("hasReceived")){
+// cacheData("hasReceived", true);
+// hasFetched = false;
+// validation();
+// }
+// },[]
+// );
+
+// useEffect(() => {
+// eventBus.on("assign_project_one", handler);
+// return () => eventBus.off("assign_project_one", handler);
+// }, [handler]);
+
+// return { profile, loading, error };
+// };
+
+export const useProfile = () => {
+ const loggedUser = useSelector((store) => store.globalVariables.loginUser);
+ const queryClient = useQueryClient();
+
+ const {
+ data: profile,
+ error,
+ isLoading,
+ refetch,
+ } = useQuery({
+ queryKey: ["profile"],
+ queryFn: async () => {
+ const response = await AuthRepository.profile();
+ cacheProfileData(response.data);
+ return response.data;
+ },
+ initialData: loggedUser || undefined,
+ enabled: !loggedUser,
+ staleTime: 10 * 60 * 1000,
+ });
+
+ const handler = useCallback(() => {
+ queryClient.invalidateQueries({ queryKey: ["profile"] });
+ }, [queryClient]);
useEffect(() => {
eventBus.on("assign_project_one", handler);
return () => eventBus.off("assign_project_one", handler);
}, [handler]);
- return { profile, loading, error };
+ return {
+ profile,
+ loading: isLoading,
+ error,
+ refetch,
+ };
};
diff --git a/src/hooks/useProjects.js b/src/hooks/useProjects.js
index 21c8e396..2cc5ee1d 100644
--- a/src/hooks/useProjects.js
+++ b/src/hooks/useProjects.js
@@ -6,194 +6,538 @@ import { useDispatch, useSelector } from "react-redux";
import { setProjectId } from "../slices/localVariablesSlice";
import EmployeeList from "../components/Directory/EmployeeList";
import eventBus from "../services/eventBus";
+import {Mutation, useMutation, useQuery, useQueryClient} from "@tanstack/react-query";
+import showToast from "../services/toastService";
+
+// export const useProjects = () => {
+// const loggedUser = useSelector((store) => store.globalVariables.loginUser);
+// const [projects, setProjects] = useState([]);
+// const [loading, setLoading] = useState(true);
+// const [error, setError] = useState("");
+
+// const fetchData = async () => {
+// const projectIds = loggedUser?.projects || [];
+
+// const filterProjects = (projectsList) => {
+// return projectsList
+// .filter((proj) => projectIds.includes(String(proj.id)))
+// .sort((a, b) => a?.name?.localeCompare(b.name));
+// };
+
+// const projects_cache = getCachedData("projectslist");
+
+// if (!projects_cache) {
+// setLoading(true);
+// try {
+// const response = await ProjectRepository.getProjectList();
+// const allProjects = response.data;
+// const filtered = filterProjects(allProjects);
+// setProjects(filtered);
+// cacheData("projectslist", allProjects);
+// } catch (err) {
+// setError("Failed to fetch data.");
+// } finally {
+// setLoading(false);
+// }
+// } else {
+// if (!projects.length) {
+// const filtered = filterProjects(projects_cache);
+// setProjects(filtered);
+// setLoading(false);
+// }
+// }
+// };
+// useEffect(() => {
+// if (loggedUser) {
+// fetchData();
+// }
+// }, [loggedUser]);
+
+// return { projects, loading, error, refetch: fetchData };
+// };
+
+// export const useEmployeesByProjectAllocated = (selectedProject) => {
+// const [projectEmployees, setEmployeeList] = useState([]);
+// const [loading, setLoading] = useState(true);
+// const [projects, setProjects] = useState([]);
+
+// const fetchData = async (projectid) => {
+// try {
+// let EmployeeByProject_Cache = getCachedData("empListByProjectAllocated");
+// if (
+// !EmployeeByProject_Cache ||
+// !EmployeeByProject_Cache.projectId === projectid
+// ) {
+// let response = await ProjectRepository.getProjectAllocation(projectid);
+// setEmployeeList(response.data);
+// cacheData("empListByProjectAllocated", {
+// data: response.data,
+// projectId: projectid,
+// });
+// setLoading(false);
+// } else {
+// setEmployeeList(EmployeeByProject_Cache.data);
+// setLoading(false);
+// }
+// } catch (err) {
+// setError("Failed to fetch data.");
+// setLoading(false);
+// }
+// };
+
+// useEffect(() => {
+// if (selectedProject) {
+// fetchData(selectedProject);
+// }
+// }, [selectedProject]);
+
+// return { projectEmployees, loading, projects };
+// };
+
+// export const useProjectDetails = (projectId) => {
+// const { profile } = useProfile();
+// const [projects_Details, setProject_Details] = useState(null);
+// const [loading, setLoading] = useState(true);
+// const [error, setError] = useState("");
+
+// const fetchData = async () => {
+// setLoading(true);
+
+// const project_cache = getCachedData("projectInfo");
+// if (!project_cache || project_cache?.projectId != projectId) {
+// ProjectRepository.getProjectByprojectId(projectId)
+// .then((response) => {
+// setProject_Details(response.data);
+// cacheData("projectInfo", {
+// projectId: projectId,
+// data: response.data,
+// });
+// setLoading(false);
+// })
+// .catch((error) => {
+// console.error(error);
+// setError("Failed to fetch data.");
+// setLoading(false);
+// });
+// } else {
+// setProject_Details(project_cache.data);
+// setLoading(false);
+// }
+// };
+
+// useEffect(() => {
+// if (profile && projectId != undefined) {
+// fetchData();
+// }
+// }, [projectId, profile]);
+
+// return { projects_Details, loading, error, refetch: fetchData };
+// };
+
+// export const useProjectsByEmployee = (employeeId) => {
+// const [projectList, setProjectList] = useState([]);
+// const [loading, setLoading] = useState(false);
+// const [error, setError] = useState("");
+
+// const fetchProjects = async (id) => {
+// try {
+// setLoading(true);
+// setError(""); // clear previous error
+// const res = await ProjectRepository.getProjectsByEmployee(id);
+// setProjectList(res.data);
+// cacheData("ProjectsByEmployee", { data: res.data, employeeId: id });
+// setLoading(false);
+// } catch (err) {
+// setError(err?.message || "Failed to fetch projects");
+// setLoading(false);
+// }
+// };
+
+// useEffect(() => {
+// if (!employeeId) return;
+
+// const cache_project = getCachedData("ProjectsByEmployee");
+
+// if (!cache_project?.data || cache_project?.employeeId !== employeeId) {
+// fetchProjects(employeeId);
+// } else {
+// setProjectList(cache_project.data);
+// }
+// }, [employeeId]);
+
+// return {
+// projectList,
+// loading,
+// error,
+// refetch: fetchProjects,
+// };
+// };
+
+// export const useProjectName = () => {
+// const [loading, setLoading] = useState(true);
+// const [projectNames, setProjectName] = useState([]);
+// const [Error, setError] = useState();
+// const dispatch = useDispatch();
+
+// const fetchData = async () => {
+// try {
+// let response = await ProjectRepository.projectNameList();
+// setProjectName(response.data);
+// cacheData("basicProjectNameList", response.data);
+// setLoading(false);
+// if(response.data.length === 1){
+// dispatch(setProjectId(response.data[0]?.id));
+// }
+// } catch (err) {
+// setError("Failed to fetch data.");
+// setLoading(false);
+// }
+// };
+// useEffect(() => {
+// fetchData();
+// }, []);
+
+// return { projectNames, loading, Error, fetchData };
+// };
+
+// ------------------------------Query-------------------
export const useProjects = () => {
const loggedUser = useSelector((store) => store.globalVariables.loginUser);
- const [projects, setProjects] = useState([]);
- const [loading, setLoading] = useState(true);
- const [error, setError] = useState("");
- const fetchData = async () => {
- const projectIds = loggedUser?.projects || [];
-
- const filterProjects = (projectsList) => {
- return projectsList
- .filter((proj) => projectIds.includes(String(proj.id)))
- .sort((a, b) => a?.name?.localeCompare(b.name));
- };
-
- const projects_cache = getCachedData("projectslist");
-
- if (!projects_cache) {
- setLoading(true);
- try {
- const response = await ProjectRepository.getProjectList();
- const allProjects = response.data;
- const filtered = filterProjects(allProjects);
- setProjects(filtered);
- cacheData("projectslist", allProjects);
- } catch (err) {
- setError("Failed to fetch data.");
- } finally {
- setLoading(false);
- }
- } else {
- if (!projects.length) {
- const filtered = filterProjects(projects_cache);
- setProjects(filtered);
- setLoading(false);
- }
- }
- };
- useEffect(() => {
- if (loggedUser) {
- fetchData();
- }
- }, [loggedUser]);
-
- return { projects, loading, error, refetch: fetchData };
-};
-
-export const useEmployeesByProjectAllocated = (selectedProject) => {
- const [projectEmployees, setEmployeeList] = useState([]);
- const [loading, setLoading] = useState(true);
- const [projects, setProjects] = useState([]);
-
- const fetchData = async (projectid) => {
- try {
- let EmployeeByProject_Cache = getCachedData("empListByProjectAllocated");
- if (
- !EmployeeByProject_Cache ||
- !EmployeeByProject_Cache.projectId === projectid
- ) {
- let response = await ProjectRepository.getProjectAllocation(projectid);
- setEmployeeList(response.data);
- cacheData("empListByProjectAllocated", {
- data: response.data,
- projectId: projectid,
- });
- setLoading(false);
- } else {
- setEmployeeList(EmployeeByProject_Cache.data);
- setLoading(false);
- }
- } catch (err) {
- setError("Failed to fetch data.");
- setLoading(false);
- }
- };
-
- useEffect(() => {
- if (selectedProject) {
- fetchData(selectedProject);
- }
- }, [selectedProject]);
-
- return { projectEmployees, loading, projects };
-};
-
-export const useProjectDetails = (projectId) => {
- const { profile } = useProfile();
- const [projects_Details, setProject_Details] = useState(null);
- const [loading, setLoading] = useState(true);
- const [error, setError] = useState("");
-
- const fetchData = async () => {
- setLoading(true);
-
- const project_cache = getCachedData("projectInfo");
- if (!project_cache || project_cache?.projectId != projectId) {
- ProjectRepository.getProjectByprojectId(projectId)
- .then((response) => {
- setProject_Details(response.data);
- cacheData("projectInfo", {
- projectId: projectId,
- data: response.data,
- });
- setLoading(false);
- })
- .catch((error) => {
- console.error(error);
- setError("Failed to fetch data.");
- setLoading(false);
- });
- } else {
- setProject_Details(project_cache.data);
- setLoading(false);
- }
- };
-
- useEffect(() => {
- if (profile && projectId != undefined) {
- fetchData();
- }
- }, [projectId, profile]);
-
- return { projects_Details, loading, error, refetch: fetchData };
-};
-
-export const useProjectsByEmployee = (employeeId) => {
- const [projectList, setProjectList] = useState([]);
- const [loading, setLoading] = useState(false);
- const [error, setError] = useState("");
-
- const fetchProjects = async (id) => {
- try {
- setLoading(true);
- setError(""); // clear previous error
- const res = await ProjectRepository.getProjectsByEmployee(id);
- setProjectList(res.data);
- cacheData("ProjectsByEmployee", { data: res.data, employeeId: id });
- setLoading(false);
- } catch (err) {
- setError(err?.message || "Failed to fetch projects");
- setLoading(false);
- }
- };
-
- useEffect(() => {
- if (!employeeId) return;
-
- const cache_project = getCachedData("ProjectsByEmployee");
-
- if (!cache_project?.data || cache_project?.employeeId !== employeeId) {
- fetchProjects(employeeId);
- } else {
- setProjectList(cache_project.data);
- }
- }, [employeeId]);
+ const {
+ data: projects = [],
+ isLoading: loading,
+ error,
+ refetch,
+ } = useQuery({
+ queryKey: ['ProjectsList'],
+ queryFn: async () => {
+ const response = await ProjectRepository.getProjectList();
+ return response.data;
+ },
+ enabled: !!loggedUser,
+ });
return {
- projectList,
+ projects,
loading,
error,
- refetch: fetchProjects,
+ refetch,
};
};
-export const useProjectName = () => {
- const [loading, setLoading] = useState(true);
- const [projectNames, setProjectName] = useState([]);
- const [Error, setError] = useState();
- const dispatch = useDispatch();
-
- const fetchData = async () => {
- try {
- let response = await ProjectRepository.projectNameList();
- setProjectName(response.data);
- cacheData("basicProjectNameList", response.data);
- setLoading(false);
- if(response.data.length === 1){
- dispatch(setProjectId(response.data[0]?.id));
- }
- } catch (err) {
- setError("Failed to fetch data.");
- setLoading(false);
+export const useEmployeesByProjectAllocated = (selectedProject) =>
+{
+ const {data = [], isLoading, refetch, error} = useQuery( {
+ queryKey: ["empListByProjectAllocated", selectedProject ],
+ queryFn: async () =>
+ {
+ const res = await ProjectRepository.getProjectAllocation( selectedProject );
+ return res.data || res
+ },
+ enabled: !!selectedProject,
+ onError: ( error ) =>
+ {
+ showToast(error.message || "Error while Fetching project Allocated Employees", "error");
}
- };
- useEffect(() => {
- fetchData();
- }, []);
+ } )
+
+ return {
+ projectEmployees: data,
+ loading:isLoading,
+ error,
+ refetch
+ }
+}
- return { projectNames, loading, Error, fetchData };
+export const useProjectDetails = ( projectId,isAuto = true ) =>
+{
+ const {data: projects_Details, isLoading, error, refetch} = useQuery( {
+ queryKey: [ "projectInfo", projectId ],
+ queryFn: async () =>
+ {
+ const res = await ProjectRepository.getProjectByprojectId( projectId );
+ return res.data || res;
+ },
+ enabled: !!projectId && isAuto,
+ onError: ( error ) =>
+ {
+ showToast(error.message || "Error while Fetching project Details", "error");
+ }
+ } )
+ return { projects_Details, loading:isLoading, error, refetch };
+}
+
+export const useProjectsByEmployee = (employeeId) =>
+{
+ const { data:projectNameList =[],isLoading,error,refetch} = useQuery( {
+ queryKey: [ "ProjectsByEmployee", employeeId ],
+ queryFn: async () =>
+ {
+ const res = await ProjectRepository.getProjectsByEmployee( employeeId );
+ return res.data || res;
+ },
+ enabled: !!employeeId,
+ onError: ( error ) =>
+ {
+ showToast(error.message || "Error while Fetching project Employee", "error");
+ }
+ })
+ return {projectList, loading:isLoading,error,refetch }
+}
+
+export const useProjectName = () =>
+{
+ const {data = [],isLoading,error,refetch} = useQuery( {
+ queryKey: [ "basicProjectNameList" ],
+ queryFn: async () =>
+ {
+ const res = await ProjectRepository.projectNameList();
+ return res.data || res;
+ },
+ onError: ( error ) =>
+ {
+ showToast(error.message || "Error while Fetching project Name", "error");
+ }
+ } )
+ return {projectNames:data,loading:isLoading,Error:error,refetch}
+}
+
+
+
+export const useProjectInfra = (projectId) => {
+ const {
+ data: projectInfra,
+ isLoading,
+ error,
+ } = useQuery({
+ queryKey: ["ProjectInfra", projectId],
+ queryFn: async () => {
+ const res = await ProjectRepository.getProjectInfraByproject(projectId);
+ return res.data;
+ },
+ enabled: !!projectId ,
+ onError: (error) => {
+ showToast(error.message || "Error while fetching project infra", "error");
+ },
+ });
+
+ return { projectInfra, isLoading, error };
};
+
+
+export const useProjectTasks = (workAreaId,IsExpandedArea=false) =>
+{
+ const { data:ProjectTaskList,isLoading,error } = useQuery( {
+ queryKey: [ "WorkItems",workAreaId ],
+ queryFn: async () =>
+ {
+ const res = await ProjectRepository.getProjectTasksByWorkArea(workAreaId);
+ return res.data;
+ },
+ enabled: !!workAreaId && !!IsExpandedArea,
+ onError: ( error ) =>
+ {
+ showToast(error.message || "Error while Fetching project Tasks", "error");
+ }
+ } )
+ return {ProjectTaskList,isLoading,error}
+}
+
+
+// -- -------------Mutation-------------------------------
+
+
+
+export const useCreateProject = ({ onSuccessCallback }) => {
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: async (newProject) => {
+ const res = await ProjectRepository.manageProject(newProject);
+ return res.data;
+ },
+ onSuccess: (data) => {
+ // Invalidate the cache
+ queryClient.invalidateQueries( {queryKey: [ 'ProjectsList' ]} );
+ queryClient.invalidateQueries({queryKey:['basicProjectNameList']});
+
+ // Emit event for consumers (like useProjects or others)
+ eventBus.emit("project", {
+ keyword: "Create_Project",
+ response: data,
+ });
+
+ showToast("Project Created successfully.", "success");
+
+ if (onSuccessCallback) {
+ onSuccessCallback(data);
+ }
+ },
+ onError: (error) => {
+ showToast(error.message || "Error while creating project", "error");
+ },
+ });
+};
+
+
+export const useUpdateProject = ({ onSuccessCallback }) => {
+ const queryClient = useQueryClient();
+ const {
+ mutate,
+ isPending,
+ isSuccess,
+ isError,
+ } = useMutation({
+ mutationFn: async ( {projectId, updatedData} ) =>
+ {
+ return await ProjectRepository.updateProject(projectId, updatedData);
+ },
+
+ onSuccess: ( data, variables ) =>
+ {
+ const { projectId } = variables;
+
+ queryClient.invalidateQueries({queryKey:["ProjectsList"]});
+ queryClient.invalidateQueries( {queryKey: [ "projectInfo", projectId ]} );
+ queryClient.invalidateQueries({queryKey:['basicProjectNameList']});
+
+ eventBus.emit("project", {
+ keyword: "Update_Project",
+ response: data,
+ });
+
+ showToast("Project updated successfully.", "success");
+
+ if (onSuccessCallback) {
+ onSuccessCallback(data);
+ }
+ },
+
+ onError: ( error ) =>
+ {
+ console.log(error)
+ showToast(error?.message || "Error while updating project", "error");
+ },
+ });
+
+ return {
+ mutate,
+ isPending,
+ isSuccess,
+ isError,
+ };
+};
+
+
+export const useManageProjectInfra = ( {onSuccessCallback} ) =>
+{
+ const queryClient = useQueryClient();
+ return useMutation({
+ mutationFn: async ( {infraObject, projectId} ) =>
+ {
+ return await ProjectRepository.manageProjectInfra(infraObject);
+ },
+ onSuccess: ( data, variables ) =>
+ {
+ const { projectId } = variables;
+ queryClient.invalidateQueries({queryKey:["ProjectInfra", projectId]});
+ if (onSuccessCallback) onSuccessCallback(data,variables);
+ },
+ onError: (error) => {
+ showToast(error.message || "Failed to update Project Infra", "error");
+ },
+ });
+};
+
+
+export const useManageProjectAllocation = ({
+ onSuccessCallback,
+ onErrorCallback,
+}) => {
+ const queryClient = useQueryClient();
+
+ const {
+ mutate,
+ isPending,
+ isSuccess,
+ isError,
+ } = useMutation({
+ mutationFn: async ( {items} ) =>
+ {
+ const response = await ProjectRepository.manageProjectAllocation(items);
+ return response.data;
+ },
+ onSuccess: (data, variables, context) => {
+ queryClient.invalidateQueries({queryKey:['empListByProjectAllocated']});
+ queryClient.removeQueries({queryKey:["projectEmployees"]})
+ if (variables?.added) {
+ showToast('Employee Assigned Successfully', 'success');
+ } else {
+ showToast('Removed Employee Successfully', 'success');
+ }
+
+ if (onSuccessCallback) onSuccessCallback(data, context);
+ },
+ onError: (error) => {
+ const message =
+ error?.response?.data?.message || error.message || 'Error occurred during API call';
+ showToast(message, 'error');
+ if (onErrorCallback) onErrorCallback(error);
+ },
+ });
+
+ return {
+ mutate,
+ isPending,
+ isSuccess,
+ isError,
+ };
+};
+
+export const useManageTask = ({onSuccessCallback}) =>
+{
+ const queryClient = useQueryClient();
+
+ return useMutation( {
+ mutationFn: async ( payload ) => await ProjectRepository.manageProjectTasks( payload ),
+ onSuccess: ( data, variables ) =>
+ {
+ queryClient.invalidateQueries({ queryKey: ["WorkItems"] })
+ if (onSuccessCallback) onSuccessCallback(data);
+ },
+ onError: (error) =>
+ {
+ const message =
+ error?.response?.data?.message || error.message || 'Error occurred during API call';
+ showToast(message, 'error');
+ }
+
+ })
+}
+
+export const useDeleteProjectTask = (onSuccessCallback) => {
+ const queryClient = useQueryClient();
+
+ return useMutation({
+ mutationFn: async ( {workItemId, workAreaId} ) =>
+ {
+ return await ProjectRepository.deleteProjectTask(workItemId);
+ },
+ onSuccess: ( _, variables ) =>
+ {
+ showToast("Task deleted successfully", "success");
+ queryClient.invalidateQueries({queryKey:[ "WorkItems",variables.workAreaId]});
+ if (onSuccessCallback) onSuccessCallback();
+ },
+ onError: (error) => {
+ showToast(
+ error?.response?.data?.message || error.message || "Failed to delete task",
+ "error"
+ );
+ if (onSuccessCallback) onSuccessCallback();
+ },
+ });
+};
+
diff --git a/src/hooks/useTasks.js b/src/hooks/useTasks.js
index 04d7715e..1cf531c0 100644
--- a/src/hooks/useTasks.js
+++ b/src/hooks/useTasks.js
@@ -2,103 +2,192 @@ import { useEffect, useState } from "react";
import { TasksRepository } from "../repositories/TaskRepository";
import { cacheData, getCachedData } from "../slices/apiDataManager";
import {MasterRespository} from "../repositories/MastersRepository";
-// import {formatDate} from "../utils/dateUtils";
+import { useMutation, useQuery, useQueryClient } from "@tanstack/react-query";
+import showToast from "../services/toastService";
+import {useSelector} from "react-redux";
+
+
+// ---------Query---------------------------------
export const useTaskList = (projectId, dateFrom, toDate) => {
- const [TaskList, setTaskList] = useState([]);
- const [loading, setLoading] = useState(false);
- const [error, setError] = useState(null);
+ const enabled = !!projectId && !!dateFrom && !!toDate;
- const fetchList = async (projectId, dateFrom, toDate) => {
- const taskList_cached = getCachedData("taskList");
- // if (!taskList_cached || taskList_cached?.projectId !== projectId) {
- try {
- setLoading(true);
- const resp = await TasksRepository.getTaskList(
- projectId,
- dateFrom,
- toDate
- );
- setTaskList(resp.data);
- cacheData("taskList", { projectId: projectId, data: resp.data });
- setLoading(false);
- } catch (err) {
- setLoading(false);
- setError(err);
- }
- // } else {
- // setTaskList(taskList_cached.data);
- // }
- };
- useEffect( () =>
- {
+ const {
+ data: TaskList = [],
+ isLoading: loading,
+ error,
+ refetch,
+ } = useQuery({
+ queryKey: ["taskList", projectId, dateFrom, toDate],
+ queryFn: async () => {
+ const response = await TasksRepository.getTaskList(
+ projectId,
+ dateFrom,
+ toDate
+ );
+ return response.data;
+ },
+ enabled,
+
+ });
- if (projectId && dateFrom && toDate) {
- fetchList(projectId, dateFrom, toDate);
- }
-
- }, [projectId, dateFrom, toDate]);
+ return { TaskList, loading, error, refetch };
+};
- return { TaskList, loading, error, refetch:fetchList};
+export const useTaskById = (TaskId) => {
+ const {
+ data: Task = null,
+ isLoading: loading,
+ error,
+ refetch,
+ } = useQuery({
+ queryKey: ["taskDetails", TaskId],
+ queryFn: async () => {
+ const res = await TasksRepository.getTaskById(TaskId);
+ return res.data;
+ },
+ enabled: !!TaskId,
+ });
+
+ return { Task, loading, error, refetch };
+};
+
+// export const useActivities = () => {
+// return useQuery({
+// queryKey: ["activitiesMaster"],
+// queryFn: async () => {
+// const response = await ActivityRepository.getActivities();
+// return response.data;
+// },
+
+// });
+// };
+
+export const useAuditStatus = () => {
+ const {
+ data: status = [],
+ isLoading: loading,
+ error,
+ refetch,
+ } = useQuery({
+ queryKey: ["AuditStatus"],
+ queryFn: async () => {
+ const res = await MasterRespository.getAuditStatus();
+ return res.data;
+ },
+
+ });
+
+ return { status, loading, error, refetch };
};
-export const useTaskById = (TaskId) =>
+// -----------------------Mutation------------------------
+const toDate = new Date().toISOString().split('T')[0];
+const dateFrom = new Date(Date.now() - 6 * 24 * 60 * 60 * 1000).toISOString().split('T')[0];
+
+
+
+export const useReportTask = ( {onSuccessCallback, onErrorCallback} = {} ) =>
{
- const [Task, setTask] = useState([]);
- const [loading, setLoading] = useState(false);
- const [ error, setError ] = useState( null );
-
-
-
- const fetchTask = async(TaskId) =>
- {
- try
+ const queryClient = useQueryClient();
+ const {
+ mutate,
+ isPending,
+ isSuccess,
+ isError,
+ error,
+ } = useMutation({
+ mutationFn: async ( {reportData,workAreaId} ) =>
{
- let res = await TasksRepository.getTaskById( TaskId );
- setTask( res.data );
-
- } catch ( error )
+ debugger
+ return await TasksRepository.reportTask(reportData);
+ },
+ onSuccess: ( data, variables ) =>
{
- setError(err)
- }
- }
- useEffect( () =>
- {
- if ( TaskId )
- {
- fetchTask(TaskId)
- }
- }, [ TaskId ] )
- return { Task,loading}
-}
+ const {workAreaId} = variables;
+ queryClient.invalidateQueries( {queryKey: [ "taskList" ]} );
+ queryClient.invalidateQueries( {queryKey: [ "WorkItems", workAreaId ]} );
+ queryClient.invalidateQueries( {queryKey: [ 'ProjectsList' ]} );
+ showToast( "Task Reported Successfully.", "success" );
+ if (onSuccessCallback) onSuccessCallback(data);
+ },
+ onError: (error) => {
+ const msg =
+ error?.response?.data?.message || error.message || "Error occurred during API call";
+ showToast( msg, "error" );
+ },
+ });
-export const useAuditStatus = () =>
+ return {
+ mutate,
+ isPending,
+ isSuccess,
+ isError,
+ error,
+ };
+};
+
+export const useSubmitTaskComment = ({ actionAllow, onSuccessCallback }) => {
+ const queryClient = useQueryClient();
+ const { mutate, isPending } = useMutation({
+ mutationFn: async ({ data, commentsData }) => {
+ const payload = {
+ ...data,
+ [actionAllow ? "id" : "taskAllocationId"]: commentsData?.id,
+ ...(actionAllow ? {} : { commentDate: new Date().toISOString() }),
+ };
+
+ const response = actionAllow
+ ? await TasksRepository.auditTask(payload)
+ : await TasksRepository.taskComments(payload);
+
+ return response.data;
+ },
+
+ onSuccess: ( data,variables ) =>
+ {
+
+ const workAreaId = variables?.commentsData?.workItem?.workArea?.id;
+ queryClient.invalidateQueries({ queryKey: ["taskList"] });
+ if (actionAllow) {
+ showToast( "Review submitted successfully.", "success" );
+
+ } else
+ {
+ showToast("Comment sent successfully.", "success");
+ }
+
+ onSuccessCallback?.(data);
+ },
+
+ onError: (error) => {
+ const msg = error?.response?.data?.message || error.message || "Error during API call";
+ showToast(msg, "error");
+ },
+ });
+
+ return { submitComment: mutate, isPending };
+};
+
+export const useCreateTask = ( {onSuccessCallback, onErrorCallback} = {} ) =>
{
- const [ status, setStatus ] = useState( [] );
- const [ error, setError ] = useState( '' );
- const [ loading, setLoading ] = useState( false )
-
- const fetchStatus = async() =>
- {
- try
+ const queryClient = useQueryClient();
+ return useMutation({
+ mutationFn: async ({payload,workAreaId}) => {
+ return await TasksRepository.assignTask(payload);
+ },
+ onSuccess: ( _, variables ) =>
{
- const res = await MasterRespository.getAuditStatus()
- setStatus( res.data )
- cacheData("AuditStatus",res.data)
- } catch ( err )
+ queryClient.invalidateQueries( {queryKey: [ "taskList" ]} );
+ queryClient.invalidateQueries( {queryKey: [ "WorkItems", variables?.workAreaId ]} );
+ showToast( "Task Assigned Successfully.", "success" );
+ if (onSuccessCallback) onSuccessCallback(variables);
+ },
+ onError: ( error ) =>
{
- setError(err)
- }
- }
-useEffect(() => {
- const cache_status = getCachedData('AuditStatus');
- if (cache_status) {
- setStatus(cache_status);
- } else {
- fetchStatus();
- }
-}, []);
-
- return {status,error,loading}
-}
\ No newline at end of file
+ showToast("Something went wrong. Please try again.", "error");
+ if (onErrorCallback) onErrorCallback(error);
+ },
+ });
+};
\ No newline at end of file
diff --git a/src/layouts/AuthLayout.jsx b/src/layouts/AuthLayout.jsx
index 2b2ec80f..2640081b 100644
--- a/src/layouts/AuthLayout.jsx
+++ b/src/layouts/AuthLayout.jsx
@@ -1,5 +1,17 @@
import React from "react";
-import { Outlet } from "react-router-dom";
+import {Outlet} from "react-router-dom";
+import {QueryClient} from '@tanstack/react-query';
+
+export const queryClient = new QueryClient({
+ defaultOptions: {
+ queries: {
+ staleTime: 5 * 60 * 1000, // 5 min: data considered fresh
+ refetchOnWindowFocus: true, // refresh on tab switch
+ refetchOnReconnect: true, // re-fetch if network was lost
+ retry: false,
+ },
+ },
+});
const AuthLayout = () => {
return (
diff --git a/src/pages/Activities/DailyTask.jsx b/src/pages/Activities/DailyTask.jsx
index 4d2b476a..dba18d18 100644
--- a/src/pages/Activities/DailyTask.jsx
+++ b/src/pages/Activities/DailyTask.jsx
@@ -9,10 +9,11 @@ import ReportTaskComments from "../../components/Activities/ReportTaskComments";
import DateRangePicker from "../../components/common/DateRangePicker";
import { useSearchParams } from "react-router-dom";
import moment from "moment";
-import FilterIcon from "../../components/common/FilterIcon"; // Import the FilterIcon component
+import FilterIcon from "../../components/common/FilterIcon";
import GlobalModel from "../../components/common/GlobalModel";
import AssignTask from "../../components/Project/AssignTask";
import SubTask from "../../components/Activities/SubTask";
+import {formatNumber} from "../../utils/dateUtils";
const DailyTask = () => {
const [searchParams] = useSearchParams();
@@ -20,14 +21,7 @@ const DailyTask = () => {
const selectedProject = useSelector(
(store) => store.localVariables.projectId
);
- const {
- projects,
- loading: project_loading,
- error: projects_Error,
- } = useProjects();
- const [initialized, setInitialized] = useState(false);
- const dispatch = useDispatch();
const [filters, setFilters] = useState({
selectedBuilding: "",
@@ -35,23 +29,7 @@ const DailyTask = () => {
selectedActivities: [],
});
- useEffect(() => {
- if (!project_loading && projects.length > 0 && !initialized) {
- if (projectIdFromUrl) {
- dispatch(setProjectId(projectIdFromUrl));
- } else if (selectedProject === 1 || selectedProject === undefined) {
- dispatch(setProjectId(projects[0].id));
- }
- setInitialized(true);
- }
- }, [
- project_loading,
- projects,
- projectIdFromUrl,
- selectedProject,
- initialized,
- dispatch,
- ]);
+
const [dateRange, setDateRange] = useState({ startDate: "", endDate: "" });
@@ -61,10 +39,11 @@ const DailyTask = () => {
error: task_error,
refetch,
} = useTaskList(
- initialized ? selectedProject : null,
- initialized ? dateRange.startDate : null,
- initialized ? dateRange.endDate : null
- );
+ selectedProject || null,
+ dateRange?.startDate || null,
+ dateRange?.endDate || null
+ );
+
const [TaskLists, setTaskLists] = useState([]);
const [dates, setDates] = useState([]);
@@ -83,8 +62,8 @@ const DailyTask = () => {
}
if (filters.selectedFloors.length > 0) {
- filteredTasks = filteredTasks.filter((task) =>
- filters.selectedFloors.includes(
+ filteredTasks = filteredTasks?.filter((task) =>
+ filters.selectedFloors?.includes(
task?.workItem?.workArea?.floor?.floorName
)
);
@@ -103,9 +82,9 @@ const DailyTask = () => {
}
}, [
TaskList,
- filters.selectedBuilding,
- filters.selectedFloors,
- filters.selectedActivities,
+ filters?.selectedBuilding,
+ filters?.selectedFloors,
+ filters?.selectedActivities,
]);
useEffect(() => {
@@ -150,43 +129,32 @@ const DailyTask = () => {
const handlecloseModal = () =>
{
setIsModalOpen( false )
- refetch(selectedProject, dateRange.startDate, dateRange.endDate);
+ // refetch();
}
- const handleProjectChange = (e) => {
- const newProjectId = e.target.value;
- dispatch(setProjectId(newProjectId));
- setTaskLists([]);
- setFilters({
- selectedBuilding: "",
- selectedFloors: [],
- selectedActivities: [],
- });
- };
const handleCloseAction = (IsSubTask) => {
if (IsSubTask) {
setIsSubTaskNeeded(true);
setIsModalOpenComment(false);
} else {
- refetch(selectedProject, dateRange.startDate, dateRange.endDate);
+ // refetch();
setIsModalOpenComment(false);
}
};
const hanleCloseSubTask = () => {
setIsSubTaskNeeded(false);
setComment( null );
- refetch(selectedProject, dateRange.startDate, dateRange.endDate);
+ // refetch();
};
+
return (
<>
-
-
{isModalOpen &&
}
@@ -255,7 +223,7 @@ const DailyTask = () => {
{/* --- Spinner when tasks are loading --- */}
- {(task_loading || project_loading) && (
+ {task_loading && (
{" "}
@@ -272,7 +240,6 @@ const DailyTask = () => {
|
)}
{!task_loading &&
- !project_loading &&
TaskLists.length === 0 && (
@@ -337,9 +304,7 @@ const DailyTask = () => {
|
- {task.plannedTask || "NA"} /
- {task.workItem.plannedWork -
- task.workItem.completedWork}
+ {formatNumber(task.plannedTask)} / {formatNumber(task.workItem.plannedWork - task.workItem.completedWork)}
|
{task.completedTask} |
@@ -413,7 +378,7 @@ const DailyTask = () => {
} more`}
>
- +{task.teamMembers.length - 3}
+ + {task.teamMembers.length - 3}
)}
diff --git a/src/pages/Activities/TaskPlannng.jsx b/src/pages/Activities/TaskPlannng.jsx
index d532696e..c2b2f8da 100644
--- a/src/pages/Activities/TaskPlannng.jsx
+++ b/src/pages/Activities/TaskPlannng.jsx
@@ -1,110 +1,9 @@
-import React, { useState, useEffect } from "react";
-import "../../components/Project/ProjectInfra.css";
-
-import ProjectRepository from "../../repositories/ProjectRepository";
+import React from "react";
import Breadcrumb from "../../components/common/Breadcrumb";
import InfraPlanning from "../../components/Activities/InfraPlanning";
-import { cacheData, getCachedData } from "../../slices/apiDataManager";
-import { useProfile } from "../../hooks/useProfile";
-import { useDispatch, useSelector } from "react-redux";
-import { useProjectDetails, useProjects } from "../../hooks/useProjects";
-import { setProjectId } from "../../slices/localVariablesSlice";
-import showToast from "../../services/toastService";
+
const TaskPlannng = () => {
- const { profile } = useProfile();
- const {
- projects,
- loading: project_listLoader,
- error: projects_error,
- } = useProjects();
- const dispatch = useDispatch();
- const selectedProject = useSelector(
- (store) => store.localVariables.projectId
- );
-
-
- const [project, setProject] = useState(null);
- const [projectDetails, setProjectDetails] = useState(null);
- const [activities, setActivities] = useState(null);
-
- const [loading, setLoading] = useState(true);
- const [error, setError] = useState("");
-
- const fetchActivities = async () => {
- try {
- const activities_cache = getCachedData("activitiesMaster");
-
- if (!activities_cache) {
- ActivityeRepository.getActivities()
- .then((response) => {
- setActivities(response.data);
- cacheData("activitiesMaster", response.data);
- })
- .catch((error) => {
- setError("Failed to fetch data.");
- });
- } else {
- setActivities(activities_cache);
- }
- } catch (err) {
- setError("Failed to fetch activities.");
- } finally {
- // setLoading(false);
- }
- };
-
- const fetchData = async () => {
- try {
- const project_cache = getCachedData("projectInfo");
- if (!project_cache || !project_cache.projectId == selectedProject) {
- ProjectRepository.getProjectByprojectId(selectedProject)
- .then((response) => {
- setProjectDetails(response);
- setProject(response);
- cacheData("projectInfo", {
- data: response.data,
- projectId: selectedProject,
- });
- })
- .catch((error) => {
- const message =
- error.response?.data?.message ||
- error.message ||
- "An unexpected error occurred";
- showToast( message, "error" );
- });
- } else {
- setProjectDetails(project_cache);
- }
- } catch (err) {
- setError( "Failed to fetch data." );
- const message =
- error.response?.data?.message ||
- error.message ||
- "An unexpected error occurred";
- showToast( message, "error" );
- } finally {
- setLoading(false);
- }
- };
-
- const [activePill, setActivePill] = useState("profile");
-
- const handlePillClick = (pillKey) => {
- setActivePill(pillKey);
- };
-
- const handleDataChange = (data) => {
- fetchData();
- };
-
- useEffect(() => {
- if (projects.length != 0 && selectedProject) {
- fetchData();
- fetchActivities();
- }
- }, [selectedProject]);
return (
<>
@@ -115,17 +14,7 @@ const TaskPlannng = () => {
{ label: "Daily Task Planning" }
]}
>
- {project_listLoader && Loading.. }
- {!project_listLoader && projects.length === 0 && (
- No Project Found.
- )}
- {!project_listLoader && projects.length > 0 && (
-
- )}
+
>
);
diff --git a/src/pages/employee/EmployeeList.jsx b/src/pages/employee/EmployeeList.jsx
index 8066a2e2..ef470979 100644
--- a/src/pages/employee/EmployeeList.jsx
+++ b/src/pages/employee/EmployeeList.jsx
@@ -5,10 +5,10 @@ import { Link, NavLink, useNavigate } from "react-router-dom";
import Avatar from "../../components/common/Avatar";
import Breadcrumb from "../../components/common/Breadcrumb";
import ManageEmp from "../../components/Employee/ManageRole";
-import { useEmployeesAllOrByProjectId } from "../../hooks/useEmployees";
-import { useProjects } from "../../hooks/useProjects"; // Keep if you use projects elsewhere
-import { useProfile } from "../../hooks/useProfile"; // Keep if you use profile elsewhere
-import { hasUserPermission } from "../../utils/authUtils"; // Keep if you use this elsewhere
+import { useEmployeesAllOrByProjectId, useSuspendEmployee } from "../../hooks/useEmployees";
+import { useProjects } from "../../hooks/useProjects";
+import { useProfile } from "../../hooks/useProfile";
+import { hasUserPermission } from "../../utils/authUtils";
import { ITEMS_PER_PAGE, MANAGE_EMPLOYEES } from "../../utils/constants";
import { clearCacheKey } from "../../slices/apiDataManager";
import { useHasUserPermission } from "../../hooks/useHasUserPermission";
@@ -26,6 +26,7 @@ import { useSelector } from "react-redux";
import eventBus from "../../services/eventBus";
import { newlineChars } from "pdf-lib";
import GlobalModel from "../../components/common/GlobalModel";
+import usePagination from "../../hooks/usePagination";
const EmployeeList = () => {
const selectedProjectId = useSelector(
@@ -38,14 +39,15 @@ const EmployeeList = () => {
const { employees, loading, setLoading, error, recallEmployeeData } =
useEmployeesAllOrByProjectId(
- showAllEmployees ? null : selectedProjectId, // Use selectedProjectId here
+ showAllEmployees ? null : selectedProjectId,
showInactive
);
const [employeeList, setEmployeeList] = useState([]);
- const [modelConfig, setModelConfig] = useState();
- const [currentPage, setCurrentPage] = useState(1);
- const [itemsPerPage] = useState(ITEMS_PER_PAGE);
+ const [ modelConfig, setModelConfig ] = useState();
+ const [EmpForManageRole,setEmpForManageRole] = useState(null)
+ // const [currentPage, setCurrentPage] = useState(1);
+ // const [itemsPerPage] = useState(ITEMS_PER_PAGE);
const [isCreateModalOpen, setIsCreateModalOpen] = useState(false);
const [searchText, setSearchText] = useState("");
const [filteredData, setFilteredData] = useState([]);
@@ -53,135 +55,131 @@ const EmployeeList = () => {
const [selectedEmployeeId, setSelecedEmployeeId] = useState(null);
const [IsDeleteModalOpen, setIsDeleteModalOpen] = useState(false);
const [selectedEmpFordelete, setSelectedEmpFordelete] = useState(null);
- const [employeeLodaing, setemployeeLodaing] = useState(false);
+ const [ employeeLodaing, setemployeeLodaing ] = useState( false );
+ const {
+ mutate: suspendEmployee,
+ isPending: empLodaing
+} = useSuspendEmployee({
+ setIsDeleteModalOpen,
+ setemployeeLodaing
+} );
+
+
const navigate = useNavigate();
- /**
- * Applies the search filter to a given array of employee data.
- * @param {Array} data - The array of employee objects to filter.
- * @param {string} text - The search text.
- * @returns {Array} The filtered array.
- */
+
const applySearchFilter = (data, text) => {
- if (!text) {
- return data;
- }
- const lowercasedText = text.toLowerCase().trim(); // Ensure search text is trimmed and lowercase
+ if (!text) {
+ return data;
+ }
- return data.filter((item) => {
- // **IMPROVED FULL NAME CONSTRUCTION**
- const firstName = item.firstName || "";
- const middleName = item.middleName || "";
- const lastName = item.lastName || "";
+ const lowercasedText = text.toLowerCase().trim();
- // Join parts, then trim any excess spaces if a middle name is missing
- const fullName = `${firstName} ${middleName} ${lastName}`.toLowerCase().trim().replace(/\s+/g, ' ');
+ return data.filter((item) => {
+ const firstName = item.firstName || "";
+ const middleName = item.middleName || "";
+ const lastName = item.lastName || "";
- const email = item.email ? item.email.toLowerCase() : "";
- const phoneNumber = item.phoneNumber ? item.phoneNumber.toLowerCase() : "";
- const jobRole = item.jobRole ? item.jobRole.toLowerCase() : "";
+ const fullName = `${firstName} ${middleName} ${lastName}`
+ .toLowerCase()
+ .trim()
+ .replace(/\s+/g, " ");
+
+ const email = item.email?.toLowerCase() || "";
+ const phoneNumber = item.phoneNumber?.toLowerCase() || "";
+ const jobRole = item.jobRole?.toLowerCase() || "";
+
+ return (
+ fullName.includes(lowercasedText) ||
+ email.includes(lowercasedText) ||
+ phoneNumber.includes(lowercasedText) ||
+ jobRole.includes(lowercasedText)
+ );
+ });
+};
- return (
- fullName.includes(lowercasedText) ||
- email.includes(lowercasedText) ||
- phoneNumber.includes(lowercasedText) ||
- jobRole.includes(lowercasedText)
- );
- });
- };
const handleSearch = (e) => {
const value = e.target.value;
setSearchText(value);
setCurrentPage(1);
};
+useEffect(() => {
+ const filtered = applySearchFilter(employeeList, searchText);
+ setFilteredData(filtered);
+}, [searchText, employeeList]);
- useEffect(() => {
- setCurrentPage(1);
- if (!loading && Array.isArray(employees)) {
- const sorted = [...employees].sort((a, b) => {
- const nameA = `${a.firstName || ""}${a.middleName || ""}${a.lastName || ""}`.toLowerCase();
- const nameB = `${b.firstName || ""}${b.middleName || ""}${b.lastName || ""}`.toLowerCase();
- return nameA?.localeCompare(nameB);
- });
- setEmployeeList(sorted);
- const results = applySearchFilter(sorted, searchText);
- setFilteredData(results);
- } else if (!loading && !employees) {
- setEmployeeList([]);
- setFilteredData([]);
- }
- }, [loading, employees, showAllEmployees, searchText, selectedProjectId]); // Add selectedProjectId to dependencies
-
- const displayData = filteredData;
- const indexOfLastItem = currentPage * itemsPerPage;
- const indexOfFirstItem = indexOfLastItem - itemsPerPage;
- const currentItems = Array.isArray(displayData)
- ? displayData.slice(indexOfFirstItem, indexOfLastItem)
- : [];
-
- const paginate = (pageNumber) => setCurrentPage(pageNumber);
- const totalPages = Array.isArray(displayData)
- ? Math.ceil(displayData.length / itemsPerPage)
- : 0;
-
- const openModal = () => {
+ const displayData = searchText ? filteredData : employeeList;
+ const { currentPage, totalPages, currentItems, paginate,setCurrentPage } = usePagination(
+ displayData,
+ ITEMS_PER_PAGE
+ );
+ const openModal = () => {
setIsCreateModalOpen(true);
- };
+ };
+
+ // const closeModal = () => {
+ // setIsCreateModalOpen(false);
+
+ // const modalElement = document.getElementById("managerole-modal");
+ // if (modalElement && !showModal) {
+ // modalElement.classList.remove("show");
+ // modalElement.style.display = "none";
+ // document.body.classList.remove("modal-open");
+ // document.querySelector(".modal-backdrop")?.remove();
+ // }
+ // setShowModal(false);
+ // clearCacheKey("employeeProfile");
+ // recallEmployeeData(showInactive, showAllEmployees ? null : selectedProjectId); // Use selectedProjectId here
+ // };
+ // const handleShow = () => setShowModal(true);
+ // const handleClose = () => setShowModal( false );
+
+useEffect(() => {
+ if (!loading && Array.isArray(employees)) {
+ const sorted = [...employees].sort((a, b) => {
+ const nameA = `${a.firstName || ""}${a.middleName || ""}${a.lastName || ""}`.toLowerCase();
+ const nameB = `${b.firstName || ""}${b.middleName || ""}${b.lastName || ""}`.toLowerCase();
+ return nameA?.localeCompare(nameB);
+ });
+
+ setEmployeeList((prevList) => {
+ const prevJSON = JSON.stringify(prevList);
+ const nextJSON = JSON.stringify(sorted);
+ if (prevJSON !== nextJSON) {
+ return sorted;
+ }
+ return prevList;
+ });
+
+ setFilteredData((prev) => {
+ const prevJSON = JSON.stringify(prev);
+ const nextJSON = JSON.stringify(sorted);
+ if (prevJSON !== nextJSON) {
+ return sorted;
+ }
+ return prev;
+ });
+
+ // set currentPage to 1 only if needed
+ setCurrentPage((prevPage) => (prevPage !== 1 ? 1 : prevPage));
+ }
+}, [loading, employees, selectedProjectId, showAllEmployees]);
- const closeModal = () => {
- setIsCreateModalOpen(false);
- const modalElement = document.getElementById("managerole-modal");
- if (modalElement && !showModal) {
- modalElement.classList.remove("show");
- modalElement.style.display = "none";
- document.body.classList.remove("modal-open");
- document.querySelector(".modal-backdrop")?.remove(); // Use optional chaining for safety
- }
- setShowModal(false);
- clearCacheKey("employeeProfile");
- recallEmployeeData(showInactive, showAllEmployees ? null : selectedProjectId); // Use selectedProjectId here
- };
- const handleShow = () => setShowModal(true);
- const handleClose = () => setShowModal(false);
- const suspendEmployee = (id) => {
- setemployeeLodaing(true);
- EmployeeRepository.deleteEmployee(id)
- .then((response) => {
- showToast("Employee deleted successfully.", "success");
- clearCacheKey("employeeListByProject");
- clearCacheKey("allEmployeeList");
- clearCacheKey("allInactiveEmployeeList");
- clearCacheKey("employeeProfile");
- // Recall data based on current filter states after deletion to refresh the table
- recallEmployeeData(showInactive, showAllEmployees ? null : selectedProjectId); // Use selectedProjectId here
- setemployeeLodaing(false);
- setIsDeleteModalOpen(false);
- })
- .catch((error) => {
- const message =
- error.response?.data?.message ||
- error.message ||
- "An unexpected error occurred";
- showToast(message, "error");
- setemployeeLodaing(false);
- setIsDeleteModalOpen(false);
- });
- };
const handleConfigData = (config) => {
setModelConfig(config);
};
- useEffect(() => {
- if (modelConfig !== null) {
- openModal();
- }
- }, [modelConfig, isCreateModalOpen]);
+ // useEffect(() => {
+ // if (modelConfig !== null) {
+ // openModal();
+ // }
+ // }, [modelConfig, isCreateModalOpen]);
const tableRef = useRef(null);
const handleExport = (type) => {
@@ -215,9 +213,6 @@ const handleAllEmployeesToggle = (e) => {
setShowInactive(false);
setShowAllEmployees(isChecked);
- if (!isChecked) {
- setSelectedProject(selectedProjectId || "");
- }
};
const handleEmployeeModel = (id) => {
@@ -253,34 +248,18 @@ const handleAllEmployeesToggle = (e) => {
return (
<>
- {isCreateModalOpen && (
-
+ {EmpForManageRole && (
+ setEmpForManageRole( null )}>
+ setEmpForManageRole(null)} />
+
)}
- {/* {showModal && ( )} */}
{showModal && (
setShowModal(false)}>
setShowModal(false)}
+ onClosed={() => setShowModal( false )}
+ IsAllEmployee={showAllEmployees}
/>
)}
@@ -594,91 +573,90 @@ const handleAllEmployeesToggle = (e) => {
|
-
- {moment(item.joiningDate)?.format("DD-MMM-YYYY")}
- |
-
- {/* Assuming 'isActive' property exists to determine status */}
- {item.isActive ? (
-
- Active
-
- ) : (
-
- Inactive
-
- )}
- |
- {Manage_Employee && (
-
-
-
-
-
-
- {!item.isSystem && (
- <>
-
-
- >
- )}
-
-
+ |
+ {moment(item.joiningDate)?.format("DD-MMM-YYYY")}
|
- )}
-
- ))}
+
+ {showInactive ? (
+
+ Inactive
+
+ ) : (
+
+ Active
+
+ )}
+ |
+ {Manage_Employee && (
+
+
+
+
+
+
+ {!item.isSystem && (
+ <>
+
+
+ >
+ )}
+
+
+ |
+ )}
+
+ ))}
{/* Pagination */}
- {!loading && displayData.length > itemsPerPage && (
+ {!loading && displayData.length > ITEMS_PER_PAGE && (