This commit is contained in:
2025-12-29 16:58:56 +03:00
commit 524f3ebf23
62 changed files with 30925 additions and 0 deletions

View File

@ -0,0 +1,76 @@
import { create } from 'zustand';
import type { IdeaStatus, IdeaPriority } from '../types/idea';
interface IdeasFilters {
status?: IdeaStatus;
priority?: IdeaPriority;
module?: string;
search?: string;
}
interface IdeasSorting {
sortBy: string;
sortOrder: 'ASC' | 'DESC';
}
interface IdeasPagination {
page: number;
limit: number;
}
interface IdeasStore {
// Filters
filters: IdeasFilters;
setFilter: <K extends keyof IdeasFilters>(key: K, value: IdeasFilters[K]) => void;
clearFilters: () => void;
// Sorting
sorting: IdeasSorting;
setSorting: (sortBy: string, sortOrder?: 'ASC' | 'DESC') => void;
// Pagination
pagination: IdeasPagination;
setPage: (page: number) => void;
setLimit: (limit: number) => void;
// UI State
createModalOpen: boolean;
setCreateModalOpen: (open: boolean) => void;
}
const initialFilters: IdeasFilters = {};
const initialSorting: IdeasSorting = { sortBy: 'createdAt', sortOrder: 'DESC' };
const initialPagination: IdeasPagination = { page: 1, limit: 20 };
export const useIdeasStore = create<IdeasStore>((set) => ({
// Filters
filters: initialFilters,
setFilter: (key, value) =>
set((state) => ({
filters: { ...state.filters, [key]: value || undefined },
pagination: { ...state.pagination, page: 1 }, // Reset page on filter change
})),
clearFilters: () =>
set({ filters: initialFilters, pagination: { ...initialPagination } }),
// Sorting
sorting: initialSorting,
setSorting: (sortBy, sortOrder) =>
set((state) => ({
sorting: {
sortBy,
sortOrder: sortOrder ?? (state.sorting.sortBy === sortBy && state.sorting.sortOrder === 'ASC' ? 'DESC' : 'ASC'),
},
})),
// Pagination
pagination: initialPagination,
setPage: (page) =>
set((state) => ({ pagination: { ...state.pagination, page } })),
setLimit: (limit) =>
set((state) => ({ pagination: { ...state.pagination, limit, page: 1 } })),
// UI State
createModalOpen: false,
setCreateModalOpen: (open) => set({ createModalOpen: open }),
}));