admin/src/stores/useAppStore.ts

176 lines
4.1 KiB
TypeScript

import { create } from "zustand";
import { persist, createJSONStorage } from "zustand/middleware";
import { User } from "../services/types";
interface LoadingState {
users: boolean;
products: boolean;
orders: boolean;
notifications: boolean;
dashboard: boolean;
}
interface AppState {
sidebarOpen: boolean;
loading: LoadingState;
selectedItems: string[];
filters: {
search: string;
status: string;
dateRange: { start: string; end: string } | null;
};
currentUser: User | null;
// Actions
setSidebarOpen: (open: boolean) => void;
setLoading: (key: keyof LoadingState, value: boolean) => void;
setSelectedItems: (items: string[]) => void;
addSelectedItem: (item: string) => void;
removeSelectedItem: (item: string) => void;
clearSelectedItems: () => void;
setFilters: (filters: Partial<AppState["filters"]>) => void;
resetFilters: () => void;
setCurrentUser: (user: User | null) => void;
// Bulk actions
setGlobalLoading: (loading: boolean) => void;
}
const initialFilters = {
search: "",
status: "",
dateRange: null,
};
const initialLoading: LoadingState = {
users: false,
products: false,
orders: false,
notifications: false,
dashboard: false,
};
export const useAppStore = create<AppState>()(
persist(
(set) => ({
sidebarOpen: false,
loading: initialLoading,
selectedItems: [],
filters: initialFilters,
currentUser: null,
setSidebarOpen: (open) => set({ sidebarOpen: open }),
setLoading: (key, value) =>
set((state) => ({
loading: { ...state.loading, [key]: value },
})),
setSelectedItems: (items) => set({ selectedItems: items }),
addSelectedItem: (item) =>
set((state) => ({
selectedItems: state.selectedItems.includes(item)
? state.selectedItems
: [...state.selectedItems, item],
})),
removeSelectedItem: (item) =>
set((state) => ({
selectedItems: state.selectedItems.filter((i) => i !== item),
})),
clearSelectedItems: () => set({ selectedItems: [] }),
setFilters: (newFilters) =>
set((state) => ({
filters: { ...state.filters, ...newFilters },
})),
resetFilters: () => set({ filters: initialFilters }),
setCurrentUser: (user) => set({ currentUser: user }),
setGlobalLoading: (loading) =>
set((state) => ({
loading: Object.keys(state.loading).reduce(
(acc, key) => ({ ...acc, [key]: loading }),
{} as LoadingState
),
})),
}),
{
name: "app-storage",
storage: createJSONStorage(() => localStorage),
partialize: (state) => ({
sidebarOpen: state.sidebarOpen,
filters: state.filters,
currentUser: state.currentUser,
}),
}
)
);
export const useSidebar = () => {
const { sidebarOpen, setSidebarOpen } = useAppStore();
const toggleSidebar = () => setSidebarOpen(!sidebarOpen);
const closeSidebar = () => setSidebarOpen(false);
const openSidebar = () => setSidebarOpen(true);
return {
sidebarOpen,
toggleSidebar,
closeSidebar,
openSidebar,
};
};
export const useLoading = () => {
const { loading, setLoading, setGlobalLoading } = useAppStore();
return {
loading,
setLoading,
setGlobalLoading,
isAnyLoading: Object.values(loading).some(Boolean),
};
};
export const useSelection = () => {
const {
selectedItems,
setSelectedItems,
addSelectedItem,
removeSelectedItem,
clearSelectedItems,
} = useAppStore();
const isSelected = (item: string) => selectedItems.includes(item);
const hasSelection = selectedItems.length > 0;
return {
selectedItems,
setSelectedItems,
addSelectedItem,
removeSelectedItem,
clearSelectedItems,
isSelected,
hasSelection,
};
};
export const useFilters = () => {
const { filters, setFilters, resetFilters } = useAppStore();
return {
filters,
setFilters,
resetFilters,
hasActiveFilters:
filters.search !== "" ||
filters.status !== "" ||
filters.dateRange !== null,
};
};