Final Optimised State Code: Troubleshooting with ChatGPT
The optimisations ChatGPT introduced in my state management code included integrating useRef and useCallback. These additions prevented infinite re-renders in React and improved performance.
By using useRef, I ensured that my state initialisation only happened once, avoiding unnecessary updates. Meanwhile, useCallback helped stabilise functions, preventing re-renders triggered by function recreations.
With these refinements, my Scoped State approach remains as structured as before but now operates more efficiently. This solution has resolved my issue while keeping my React components scalable and maintainable.
import { createContext, ReactNode, useContext, useEffect, useCallback, useRef } from "react";
import { useImmer } from "use-immer";
interface EventInfoState {
activeEventId: string | undefined;
shampoo: boolean;
}
interface EventState {
eventState: EventInfoState;
resetActiveEvent: () => void;
toggleActiveEvent: (id: string) => void;
toggleShampooEvent: () => void;
}
const initialState: EventInfoState = {
activeEventId: '',
shampoo: false,
};
const LocalStateContext = createContext<EventState | undefined>(undefined);
interface EventStateProviderProps {
children: ReactNode;
eventGroup?: { eventHosts: { eventId: string }[] };
}
const EventStateProvider: React.FC<EventStateProviderProps> = ({ children, eventGroup }) => {
const [state, setState] = useImmer<EventInfoState>(initialState);
const initialized = useRef(false); // Prevent redundant state updates
const toggleActiveEvent = useCallback((id: string) => {
setState(draft => {
draft.activeEventId = id;
});
}, [setState]);
const resetActiveEvent = useCallback(() => {
setState(draft => {
draft.activeEventId = undefined;
});
}, [setState]);
const toggleShampooEvent = useCallback(() => {
setState(draft => {
draft.shampoo = !draft.shampoo;
});
}, [setState]);
// Initialize activeEventId if only one eventHost exists
useEffect(() => {
if (initialized.current) return; // Prevent multiple initializations
if (eventGroup?.eventHosts?.length === 1 && !state.activeEventId) {
setState(draft => {
draft.activeEventId = eventGroup.eventHosts[0].eventId;
});
initialized.current = true; // Mark as initialized
}
}, [eventGroup?.eventHosts, setState]);
return (
<LocalStateContext.Provider
value={{
resetActiveEvent,
toggleActiveEvent,
toggleShampooEvent,
eventState: state
}}
>
{children}
</LocalStateContext.Provider>
);
};
function useEventState(): EventState {
const context = useContext(LocalStateContext);
if (!context) {
throw new Error("useEventState must be used within an EventStateProvider");
}
return context;
}
export { EventStateProvider, useEventState };