@ramses1er/cbk-toolkit 1.12.0 → 1.13.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -168,6 +168,35 @@ interface AccessDeniedProps {
168
168
  }
169
169
  declare function AccessDenied({ logo, redirectTo, textRedirection }: AccessDeniedProps): React$1.JSX.Element;
170
170
 
171
+ type UseCurrentUser = () => {
172
+ data?: {
173
+ role: {
174
+ name: string;
175
+ };
176
+ } | null;
177
+ isLoading: boolean;
178
+ };
179
+ interface RouteGuardInputConfig {
180
+ useCurrentUser: UseCurrentUser;
181
+ pagePermissions: Record<string, string[]>;
182
+ deniedPath?: string;
183
+ }
184
+ interface RouteGuardConfig {
185
+ useCurrentUser: UseCurrentUser;
186
+ pagePermissions: Record<string, string[]>;
187
+ deniedPath: string;
188
+ }
189
+ declare function createRouteGuardConfig(input: RouteGuardInputConfig): RouteGuardConfig;
190
+ interface RouteGuardProviderProps {
191
+ children: ReactNode;
192
+ config?: RouteGuardConfig;
193
+ useCurrentUser?: UseCurrentUser;
194
+ pagePermissions?: Record<string, string[]>;
195
+ deniedPath?: string;
196
+ }
197
+ declare function RouteGuardProvider({ children, config, useCurrentUser, pagePermissions, deniedPath, }: RouteGuardProviderProps): React$1.JSX.Element;
198
+ declare function routeGuard(page: string, Component: ComponentType): (props: Record<string, unknown>) => React$1.JSX.Element;
199
+
171
200
  declare class HttpError extends Error {
172
201
  status: number;
173
202
  code?: string;
@@ -190,4 +219,4 @@ interface AuthGuardOptions {
190
219
  }
191
220
  declare function authGuard(request: NextRequest, options: AuthGuardOptions): Promise<NextResponse<unknown>>;
192
221
 
193
- export { AccessDenied, ActionsMenu, ApiError, type Column, Confirmation, DatePicker, type FetcherOptions, FieldContainer, Form, HeaderContent, HttpError, Input, Label, LoaderSubmit, Loading, Modal, type NavItem, Option, Select, SessionExpired, SideNav, type SideNavProps, type SideNavStaticConfig, Table, type TableAction, TextArea, authGuard, createSideNav, fetcher, handleServerError };
222
+ export { AccessDenied, ActionsMenu, ApiError, type Column, Confirmation, DatePicker, type FetcherOptions, FieldContainer, Form, HeaderContent, HttpError, Input, Label, LoaderSubmit, Loading, Modal, type NavItem, Option, type RouteGuardConfig, RouteGuardProvider, Select, SessionExpired, SideNav, type SideNavProps, type SideNavStaticConfig, Table, type TableAction, TextArea, type UseCurrentUser, authGuard, createRouteGuardConfig, createSideNav, fetcher, handleServerError, routeGuard };
package/dist/index.js CHANGED
@@ -1153,6 +1153,97 @@ function AccessDenied({ logo, redirectTo, textRedirection }) {
1153
1153
  ] }) });
1154
1154
  }
1155
1155
 
1156
+ // packages/ui/src/route-guard/route-guard.tsx
1157
+ import {
1158
+ createContext,
1159
+ useContext,
1160
+ useMemo as useMemo2
1161
+ } from "react";
1162
+ import { redirect, usePathname } from "next/navigation";
1163
+ import { Fragment as Fragment4, jsx as jsx20 } from "react/jsx-runtime";
1164
+ function createRouteGuardConfig(input) {
1165
+ return {
1166
+ useCurrentUser: input.useCurrentUser,
1167
+ pagePermissions: input.pagePermissions,
1168
+ deniedPath: input.deniedPath ?? "/access-denied"
1169
+ };
1170
+ }
1171
+ var RouteGuardContext = createContext(null);
1172
+ function RouteGuardProvider({
1173
+ children,
1174
+ config,
1175
+ useCurrentUser,
1176
+ pagePermissions,
1177
+ deniedPath
1178
+ }) {
1179
+ const resolved = useMemo2(() => {
1180
+ if (config) return config;
1181
+ return {
1182
+ useCurrentUser,
1183
+ pagePermissions,
1184
+ deniedPath: deniedPath ?? "/access-denied"
1185
+ };
1186
+ }, [config, useCurrentUser, pagePermissions, deniedPath]);
1187
+ if (!resolved.useCurrentUser || !resolved.pagePermissions) {
1188
+ throw new Error(
1189
+ "RouteGuardProvider requires either a `config` prop (from createRouteGuardConfig) or `useCurrentUser` + `pagePermissions` directly."
1190
+ );
1191
+ }
1192
+ return /* @__PURE__ */ jsx20(RouteGuardContext.Provider, { value: resolved, children: /* @__PURE__ */ jsx20(AutoRouteGuard, { config: resolved, children }) });
1193
+ }
1194
+ function AutoRouteGuard({
1195
+ config,
1196
+ children
1197
+ }) {
1198
+ const pathname = usePathname();
1199
+ const { data: user, isLoading } = config.useCurrentUser();
1200
+ const allowedRoles = useMemo2(
1201
+ () => findAllowedRoles(pathname, config.pagePermissions),
1202
+ [pathname, config.pagePermissions]
1203
+ );
1204
+ if (!allowedRoles) {
1205
+ return /* @__PURE__ */ jsx20(Fragment4, { children });
1206
+ }
1207
+ if (isLoading) {
1208
+ return /* @__PURE__ */ jsx20("div", { className: "flex items-center justify-center min-h-screen", children: /* @__PURE__ */ jsx20("p", { className: "text-gray-500", children: "Chargement..." }) });
1209
+ }
1210
+ if (!user || !allowedRoles.includes(user.role.name)) {
1211
+ redirect(config.deniedPath);
1212
+ }
1213
+ return /* @__PURE__ */ jsx20(Fragment4, { children });
1214
+ }
1215
+ function routeGuard(page, Component) {
1216
+ return function GuardedPage(props) {
1217
+ const config = useContext(RouteGuardContext);
1218
+ if (!config) {
1219
+ throw new Error(
1220
+ "routeGuard requires a RouteGuardProvider ancestor. Wrap your layout with <RouteGuardProvider>."
1221
+ );
1222
+ }
1223
+ const { data: user, isLoading } = config.useCurrentUser();
1224
+ const allowedRoles = findAllowedRoles(page, config.pagePermissions);
1225
+ if (!allowedRoles) {
1226
+ return /* @__PURE__ */ jsx20(Component, { ...props });
1227
+ }
1228
+ if (isLoading) {
1229
+ return /* @__PURE__ */ jsx20("div", { className: "flex items-center justify-center min-h-screen", children: /* @__PURE__ */ jsx20("p", { className: "text-gray-500", children: "Chargement..." }) });
1230
+ }
1231
+ if (!user || !allowedRoles.includes(user.role.name)) {
1232
+ redirect(config.deniedPath);
1233
+ }
1234
+ return /* @__PURE__ */ jsx20(Component, { ...props });
1235
+ };
1236
+ }
1237
+ function findAllowedRoles(page, pagePermissions) {
1238
+ const segments = page.split("/").filter(Boolean);
1239
+ for (let i = 0; i <= segments.length; i++) {
1240
+ const candidate = "/" + segments.slice(0, i).join("/");
1241
+ const roles = pagePermissions[candidate];
1242
+ if (roles) return roles;
1243
+ }
1244
+ return void 0;
1245
+ }
1246
+
1156
1247
  // packages/utils/src/fetcher.ts
1157
1248
  var ApiError = class extends Error {
1158
1249
  status;
@@ -1334,14 +1425,17 @@ export {
1334
1425
  Loading,
1335
1426
  Modal,
1336
1427
  Option,
1428
+ RouteGuardProvider,
1337
1429
  Select,
1338
1430
  SessionExpired,
1339
1431
  SideNav,
1340
1432
  Table,
1341
1433
  TextArea,
1342
1434
  authGuard,
1435
+ createRouteGuardConfig,
1343
1436
  createSideNav,
1344
1437
  fetcher,
1345
- handleServerError
1438
+ handleServerError,
1439
+ routeGuard
1346
1440
  };
1347
1441
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../packages/ui/src/layouts/side-nav.tsx","../packages/ui/src/config/create-side-nav.tsx","../packages/ui/src/table/table.tsx","../packages/ui/src/feedback/error-display.tsx","../packages/ui/src/table/actions-menu.tsx","../packages/ui/src/modals/modal.tsx","../packages/ui/src/feedback/confirmation.tsx","../packages/ui/src/headers/header-content.tsx","../packages/ui/src/forms/form.tsx","../packages/ui/src/forms/field-container.tsx","../packages/ui/src/forms/label.tsx","../packages/ui/src/forms/input.tsx","../packages/ui/src/forms/select.tsx","../packages/ui/src/forms/textarea.tsx","../packages/ui/src/forms/date-picker.tsx","../packages/ui/src/loaders/loading.tsx","../packages/ui/src/loaders/loader-submit.tsx","../packages/ui/src/pages/session-expired.tsx","../packages/ui/src/pages/access-denied.tsx","../packages/utils/src/fetcher.ts","../packages/lib/src/http-error.ts","../packages/lib/src/handle-server-error.ts","../packages/lib/src/auth-guard.ts"],"sourcesContent":["\"use client\";\r\n\r\nimport {\r\n ReactNode,\r\n useState,\r\n useEffect,\r\n createElement,\r\n isValidElement,\r\n type ComponentType,\r\n} from \"react\";\r\n\r\ntype IconType = ReactNode | ComponentType<{ size?: number }>;\r\n\r\nexport interface NavItem {\r\n id: string;\r\n label: string;\r\n title?: string;\r\n icon?: IconType;\r\n href: string;\r\n subItems?: NavItem[];\r\n}\r\n\r\nexport interface SideNavStaticConfig {\r\n brand?: {\r\n logo?: ReactNode;\r\n name?: string;\r\n tagline?: string;\r\n };\r\n mainItems: NavItem[];\r\n title?: string;\r\n footer?: { icon?: IconType; label: string; href: string }[];\r\n toggleIcon?: ReactNode;\r\n}\r\n\r\nexport interface SideNavProps extends SideNavStaticConfig {\r\n children: ReactNode;\r\n currentPath: string;\r\n}\r\n\r\nfunction isActive(href: string, currentPath: string) {\r\n return currentPath === href || currentPath.startsWith(href + \"/\");\r\n}\r\n\r\nfunction isExactActive(href: string, currentPath: string) {\r\n return currentPath === href;\r\n}\r\n\r\nexport function SideNav({\r\n children,\r\n title,\r\n mainItems,\r\n currentPath,\r\n brand,\r\n footer,\r\n toggleIcon,\r\n}: SideNavProps) {\r\n const activeMain = mainItems.find((item) => isActive(item.href, currentPath));\r\n const headerTitle = title ?? activeMain?.title ?? activeMain?.label;\r\n const [expandedSection, setExpandedSection] = useState<string | null>(\r\n activeMain?.id ?? null,\r\n );\r\n\r\n const toggleSection = (id: string) => {\r\n setExpandedSection((prev) => (prev === id ? null : id));\r\n };\r\n\r\n const [isMobileOpen, setIsMobileOpen] = useState(false);\r\n\r\n useEffect(() => {\r\n const handleEscape = (e: KeyboardEvent) => {\r\n if (e.key === \"Escape\") setIsMobileOpen(false);\r\n };\r\n document.addEventListener(\"keydown\", handleEscape);\r\n return () => document.removeEventListener(\"keydown\", handleEscape);\r\n }, []);\r\n\r\n useEffect(() => {\r\n if (isMobileOpen) {\r\n document.body.style.overflow = \"hidden\";\r\n } else {\r\n document.body.style.overflow = \"\";\r\n }\r\n return () => {\r\n document.body.style.overflow = \"\";\r\n };\r\n }, [isMobileOpen]);\r\n\r\n const closeMobileNav = () => setIsMobileOpen(false);\r\n\r\n return (\r\n <div className=\"flex min-h-screen\">\r\n <aside\r\n className={`w-64 bg-white border-r border-gray-200 flex flex-col fixed h-full z-50 transition-transform duration-300 ease-in-out md:translate-x-0 ${\r\n isMobileOpen ? \"translate-x-0\" : \"-translate-x-full\"\r\n }`}\r\n >\r\n {brand && (\r\n <div className=\"p-[6.5px] border-b border-gray-100\">\r\n <div className=\"flex flex-row gap-2 items-center\">\r\n {brand.logo &&\r\n (typeof brand.logo === \"string\" ? (\r\n <img\r\n src={brand.logo}\r\n alt={brand.name ?? \"\"}\r\n className=\"w-12.5 h-12.5\"\r\n />\r\n ) : (\r\n brand.logo\r\n ))}\r\n {brand.name && (\r\n <p className=\"text-gray-500 text-base font-semibold\">\r\n {brand.name}\r\n </p>\r\n )}\r\n </div>\r\n </div>\r\n )}\r\n\r\n <nav className=\"flex-1 p-4 overflow-y-auto\">\r\n <ul className=\"space-y-1\">\r\n {mainItems.map((item) => {\r\n const active = isActive(item.href, currentPath);\r\n const isExpanded = expandedSection === item.id;\r\n const hasSubItems = item.subItems && item.subItems.length > 0;\r\n\r\n return (\r\n <li key={item.id}>\r\n <div className=\"flex items-center gap-1\">\r\n <a\r\n href={item.href}\r\n onClick={closeMobileNav}\r\n className={`flex items-center gap-3 px-3 py-2.5 rounded-lg text-sm font-medium transition-colors flex-1 ${\r\n active\r\n ? \"bg-gray-200 text-black\"\r\n : \"text-gray-500 hover:bg-gray-100\"\r\n }`}\r\n >\r\n {item.icon &&\r\n (typeof item.icon === \"string\" ? (\r\n <span className=\"text-lg\">{item.icon}</span>\r\n ) : isValidElement(item.icon) ? (\r\n item.icon\r\n ) : (\r\n createElement(\r\n item.icon as ComponentType<{ size?: number }>,\r\n { size: 20 },\r\n )\r\n ))}\r\n {item.label}\r\n </a>\r\n {active && hasSubItems && (\r\n <button\r\n onClick={() => toggleSection(item.id)}\r\n className={`p-1.5 rounded-lg transition-colors ${\r\n active\r\n ? \"text-black hover:bg-gray-100\"\r\n : \"text-gray-500 hover:bg-gray-100\"\r\n }`}\r\n title={isExpanded ? \"Réduire\" : \"Développer\"}\r\n >\r\n {toggleIcon ? (\r\n <span\r\n className={`inline-block transition-transform duration-200 ${\r\n isExpanded ? \"rotate-0\" : \"-rotate-90\"\r\n }`}\r\n >\r\n {toggleIcon}\r\n </span>\r\n ) : (\r\n <span className=\"text-xs\">\r\n {isExpanded ? \"▼\" : \"▶\"}\r\n </span>\r\n )}\r\n </button>\r\n )}\r\n </div>\r\n\r\n {active && hasSubItems && (\r\n <div\r\n className={`grid transition-all duration-300 ease-in-out ${\r\n isExpanded ? \"grid-rows-[1fr]\" : \"grid-rows-[0fr]\"\r\n }`}\r\n >\r\n <div className=\"overflow-hidden\">\r\n <ul className=\"ml-4 mt-1 space-y-1 pl-2\">\r\n {item.subItems!.map((sub) => (\r\n <li key={sub.id}>\r\n <a\r\n href={sub.href}\r\n onClick={closeMobileNav}\r\n className={`flex items-center gap-2 px-3 py-2 rounded-lg text-sm font-medium transition-colors ${\r\n isExactActive(sub.href, currentPath)\r\n ? \"bg-gray-200 text-black\"\r\n : \"text-gray-500 hover:bg-gray-100\"\r\n }`}\r\n >\r\n {sub.label}\r\n </a>\r\n </li>\r\n ))}\r\n </ul>\r\n </div>\r\n </div>\r\n )}\r\n </li>\r\n );\r\n })}\r\n </ul>\r\n </nav>\r\n\r\n {footer && footer.length > 0 && (\r\n <div className=\"p-4 border-t border-gray-100 space-y-1\">\r\n {footer.map((item) => (\r\n <a\r\n key={item.label}\r\n href={item.href}\r\n onClick={closeMobileNav}\r\n className=\"flex items-center gap-3 px-3 py-2.5 rounded-lg text-sm font-medium text-gray-700 hover:bg-gray-100 transition-colors\"\r\n >\r\n {typeof item.icon === \"string\" ? (\r\n <span className=\"text-lg\">{item.icon}</span>\r\n ) : isValidElement(item.icon) ? (\r\n item.icon\r\n ) : (\r\n createElement(item.icon as ComponentType<{ size?: number }>, {\r\n size: 20,\r\n })\r\n )}\r\n {item.label}\r\n </a>\r\n ))}\r\n </div>\r\n )}\r\n </aside>\r\n\r\n {isMobileOpen && (\r\n <div\r\n className=\"fixed inset-0 z-40 bg-black/50 md:hidden\"\r\n onClick={closeMobileNav}\r\n aria-hidden=\"true\"\r\n />\r\n )}\r\n\r\n <div className=\"flex-1 ml-64 max-md:ml-0 min-w-0\">\r\n {headerTitle && (\r\n <header className=\"h-16 bg-white border-b border-gray-200 flex items-center justify-between px-6 fixed top-0 right-0 left-64 max-md:left-0 z-20\">\r\n <div className=\"flex items-center gap-2\">\r\n <button\r\n className=\"md:hidden p-2 -ml-2 rounded-lg hover:bg-gray-100 transition-colors\"\r\n onClick={() => setIsMobileOpen(!isMobileOpen)}\r\n aria-label={isMobileOpen ? \"Fermer le menu\" : \"Menu\"}\r\n aria-expanded={isMobileOpen}\r\n >\r\n {isMobileOpen ? (\r\n <svg\r\n className=\"w-5 h-5\"\r\n fill=\"none\"\r\n viewBox=\"0 0 24 24\"\r\n stroke=\"currentColor\"\r\n strokeWidth={2}\r\n >\r\n <path\r\n strokeLinecap=\"round\"\r\n strokeLinejoin=\"round\"\r\n d=\"M6 18L18 6M6 6l12 12\"\r\n />\r\n </svg>\r\n ) : (\r\n <svg\r\n className=\"w-5 h-5\"\r\n fill=\"none\"\r\n viewBox=\"0 0 24 24\"\r\n stroke=\"currentColor\"\r\n strokeWidth={2}\r\n >\r\n <path\r\n strokeLinecap=\"round\"\r\n strokeLinejoin=\"round\"\r\n d=\"M4 6h16M4 12h16M4 18h16\"\r\n />\r\n </svg>\r\n )}\r\n </button>\r\n <h1 className=\"text-base font-semibold text-gray-500\">\r\n {headerTitle}\r\n </h1>\r\n </div>\r\n {brand?.tagline && (\r\n <span className=\"text-sm text-gray-500 max-md:hidden\">\r\n {brand.tagline}\r\n </span>\r\n )}\r\n </header>\r\n )}\r\n {!headerTitle && (\r\n <button\r\n className=\"md:hidden fixed top-4 left-4 z-10 p-2 rounded-lg bg-white border border-gray-200 shadow-sm hover:bg-gray-100 transition-colors\"\r\n onClick={() => setIsMobileOpen(!isMobileOpen)}\r\n aria-label={isMobileOpen ? \"Fermer le menu\" : \"Menu\"}\r\n aria-expanded={isMobileOpen}\r\n >\r\n {isMobileOpen ? (\r\n <svg\r\n className=\"w-5 h-5\"\r\n fill=\"none\"\r\n viewBox=\"0 0 24 24\"\r\n stroke=\"currentColor\"\r\n strokeWidth={2}\r\n >\r\n <path\r\n strokeLinecap=\"round\"\r\n strokeLinejoin=\"round\"\r\n d=\"M6 18L18 6M6 6l12 12\"\r\n />\r\n </svg>\r\n ) : (\r\n <svg\r\n className=\"w-5 h-5\"\r\n fill=\"none\"\r\n viewBox=\"0 0 24 24\"\r\n stroke=\"currentColor\"\r\n strokeWidth={2}\r\n >\r\n <path\r\n strokeLinecap=\"round\"\r\n strokeLinejoin=\"round\"\r\n d=\"M4 6h16M4 12h16M4 18h16\"\r\n />\r\n </svg>\r\n )}\r\n </button>\r\n )}\r\n <main\r\n className={(headerTitle ? \"p-6 pt-20\" : \"p-6\") + \" overflow-x-auto\"}\r\n >\r\n {children}\r\n </main>\r\n </div>\r\n </div>\r\n );\r\n}\r\n","import { SideNav, type SideNavStaticConfig } from \"../layouts/side-nav\";\n\nexport function createSideNav(config: SideNavStaticConfig) {\n return function ConfiguredSideNav({\n children,\n currentPath,\n }: {\n children: React.ReactNode;\n currentPath: string;\n }) {\n return (\n <SideNav {...config} currentPath={currentPath}>\n {children}\n </SideNav>\n );\n };\n}\n","\"use client\";\r\n\r\nimport { Printer, ChevronLeft, ChevronRight } from \"lucide-react\";\r\nimport clsx from \"clsx\";\r\nimport { useState, useMemo, useCallback } from \"react\";\r\nimport { ErrorDisplay } from \"../feedback/error-display\";\r\nimport { ApiError } from \"../../../utils/src/fetcher\";\r\n\r\nexport type Column<T> = {\r\n header: string;\r\n accessor?: keyof T;\r\n render?: (row: T) => React.ReactNode;\r\n excludeFromPrint?: boolean;\r\n};\r\n\r\ntype TableProps<T> = {\r\n data: T[];\r\n columns: Column<T>[];\r\n loading?: boolean;\r\n error?: ApiError | null;\r\n label?: string;\r\n printable?: boolean;\r\n pageSize?: number;\r\n pageSizeOptions?: number[];\r\n showPagination?: boolean;\r\n};\r\n\r\nconst VISIBLE_PAGES = 5;\r\n\r\nexport function Table<T>({\r\n data,\r\n columns,\r\n loading,\r\n error,\r\n label,\r\n printable,\r\n pageSize = 5,\r\n pageSizeOptions = [5, 10, 20],\r\n showPagination = true,\r\n}: TableProps<T>) {\r\n const [tooltip, setTooltip] = useState<{\r\n content: string;\r\n x: number;\r\n y: number;\r\n } | null>(null);\r\n const [page, setPage] = useState(1);\r\n const [perPage, setPerPage] = useState(pageSize);\r\n\r\n const totalPages = useMemo(\r\n () => Math.max(1, Math.ceil(data.length / perPage)),\r\n [data.length, perPage],\r\n );\r\n\r\n const safePage = Math.min(page, totalPages);\r\n\r\n const displayData = useMemo(\r\n () => data.slice((safePage - 1) * perPage, safePage * perPage),\r\n [data, safePage, perPage],\r\n );\r\n\r\n const paginationRange = useMemo(() => {\r\n const half = Math.floor(VISIBLE_PAGES / 2);\r\n let start = Math.max(1, safePage - half);\r\n let end = Math.min(totalPages, start + VISIBLE_PAGES - 1);\r\n if (end - start + 1 < VISIBLE_PAGES) {\r\n start = Math.max(1, end - VISIBLE_PAGES + 1);\r\n }\r\n const range: (number | \"...\")[] = [];\r\n if (start > 1) {\r\n range.push(1);\r\n if (start > 2) range.push(\"...\");\r\n }\r\n for (let i = start; i <= end; i++) range.push(i);\r\n if (end < totalPages) {\r\n if (end < totalPages - 1) range.push(\"...\");\r\n range.push(totalPages);\r\n }\r\n return range;\r\n }, [safePage, totalPages]);\r\n\r\n const handlePageSizeChange = useCallback((value: number) => {\r\n setPerPage(value);\r\n setPage(1);\r\n }, []);\r\n\r\n const colCount = columns.length;\r\n const colWidth = colCount > 0 ? `${Math.round(100 / colCount)}%` : \"auto\";\r\n\r\n const handleMouseEnter = (\r\n e: React.MouseEvent<HTMLDivElement>,\r\n content: string,\r\n ) => {\r\n const rect = e.currentTarget.getBoundingClientRect();\r\n setTooltip({\r\n content,\r\n x: rect.left + rect.width / 2,\r\n y: rect.top,\r\n });\r\n };\r\n\r\n const handleMouseLeave = () => {\r\n setTooltip(null);\r\n };\r\n\r\n const banner = error ? (\r\n <div className=\"mb-4\">\r\n <ErrorDisplay key={error.message} error={error} />\r\n </div>\r\n ) : null;\r\n\r\n if (loading) {\r\n return (\r\n <div className=\"w-full overflow-x-auto\">\r\n {banner}\r\n <div className=\"rounded-lg shadow-md border border-gray-200\">\r\n <div className=\"flex items-center justify-center py-20 text-gray-500\">\r\n Chargement...\r\n </div>\r\n </div>\r\n </div>\r\n );\r\n }\r\n\r\n if (!data || data.length === 0) {\r\n return (\r\n <div className=\"w-full overflow-x-auto\">\r\n {banner}\r\n <div className=\"rounded-lg shadow-md border border-gray-200\">\r\n <div className=\"flex items-center justify-center py-20 text-gray-500\">\r\n Aucun élément\r\n </div>\r\n </div>\r\n </div>\r\n );\r\n }\r\n\r\n return (\r\n <div className=\"w-full overflow-x-auto\">\r\n {banner}\r\n <div className=\"flex items-center justify-between mb-2\">\r\n {label && (\r\n <div className=\"text-sm font-semibold text-gray-700\">\r\n {label}: {data.length}\r\n </div>\r\n )}\r\n {printable && (\r\n <button\r\n onClick={() => window.print()}\r\n className=\"flex items-center gap-2 px-4 py-2 text-sm font-medium text-white bg-blue-500 rounded-lg hover:bg-blue-600 transition-colors print:hidden\"\r\n >\r\n <Printer className=\"w-4 h-4\" />\r\n Imprimer\r\n </button>\r\n )}\r\n </div>\r\n <div className=\"rounded-lg shadow-md border border-gray-200\">\r\n <table className=\"w-full table-fixed divide-y divide-gray-200 print:table-fixed\">\r\n <thead className=\"bg-blue-500 rounded-t-lg\">\r\n <tr>\r\n {columns.map((col, index) => (\r\n <th\r\n key={index}\r\n style={{ width: colWidth }}\r\n className={clsx(\r\n \"px-6 py-3 text-left text-xs font-bold text-white uppercase tracking-wider truncate\",\r\n col.excludeFromPrint && \"print:hidden\",\r\n )}\r\n >\r\n {col.header}\r\n </th>\r\n ))}\r\n </tr>\r\n </thead>\r\n <tbody\r\n className={clsx(\r\n \"bg-white divide-y divide-gray-200\",\r\n printable && \"print:hidden\",\r\n )}\r\n >\r\n {displayData.map((row, rowIndex) => (\r\n <tr\r\n key={rowIndex}\r\n className=\"hover:bg-gray-100 transition-colors duration-200\"\r\n >\r\n {columns.map((col, colIndex) => {\r\n const cellContent = col.render\r\n ? col.render(row)\r\n : String(row[col.accessor!]);\r\n const textContent =\r\n typeof cellContent === \"string\" ? cellContent : \"\";\r\n\r\n return (\r\n <td\r\n key={colIndex}\r\n style={{ width: colWidth }}\r\n className={clsx(\r\n \"px-6 py-4 text-sm text-gray-700\",\r\n col.excludeFromPrint && \"print:hidden\",\r\n )}\r\n >\r\n {typeof cellContent === \"string\" ? (\r\n <div\r\n className=\"truncate\"\r\n onMouseEnter={(e) => handleMouseEnter(e, textContent)}\r\n onMouseLeave={handleMouseLeave}\r\n >\r\n {cellContent}\r\n </div>\r\n ) : (\r\n cellContent\r\n )}\r\n </td>\r\n );\r\n })}\r\n </tr>\r\n ))}\r\n </tbody>\r\n {printable && (\r\n <tbody className=\"hidden print:table-row-group\">\r\n {data.map((row, rowIndex) => (\r\n <tr key={rowIndex}>\r\n {columns.map((col, colIndex) => {\r\n const cellContent = col.render\r\n ? col.render(row)\r\n : String(row[col.accessor!]);\r\n\r\n return (\r\n <td\r\n key={colIndex}\r\n style={{ width: colWidth }}\r\n className={clsx(\r\n \"px-6 py-4 text-sm text-gray-700\",\r\n col.excludeFromPrint && \"print:hidden\",\r\n )}\r\n >\r\n {cellContent}\r\n </td>\r\n );\r\n })}\r\n </tr>\r\n ))}\r\n </tbody>\r\n )}\r\n </table>\r\n </div>\r\n\r\n {showPagination && totalPages > 1 && (\r\n <div className=\"flex items-center justify-between mt-4 text-sm print:hidden\">\r\n <div className=\"flex items-center gap-2 text-gray-600\">\r\n <span>Lignes par page :</span>\r\n <select\r\n value={perPage}\r\n onChange={(e) => handlePageSizeChange(Number(e.target.value))}\r\n className=\"border border-gray-300 rounded px-2 py-1 text-sm bg-white focus:outline-none focus:ring-2 focus:ring-blue-400\"\r\n >\r\n {pageSizeOptions.map((opt) => (\r\n <option key={opt} value={opt}>\r\n {opt}\r\n </option>\r\n ))}\r\n </select>\r\n </div>\r\n\r\n <div className=\"flex items-center gap-1\">\r\n <button\r\n onClick={() => setPage((p) => Math.max(1, p - 1))}\r\n disabled={safePage <= 1}\r\n className={clsx(\r\n \"p-1.5 rounded transition-colors\",\r\n safePage <= 1\r\n ? \"text-gray-300 cursor-not-allowed\"\r\n : \"text-gray-600 hover:bg-gray-100\",\r\n )}\r\n >\r\n <ChevronLeft className=\"w-4 h-4\" />\r\n </button>\r\n\r\n {paginationRange.map((item, i) =>\r\n item === \"...\" ? (\r\n <span key={`ellipsis-${i}`} className=\"px-2 text-gray-400\">\r\n ...\r\n </span>\r\n ) : (\r\n <button\r\n key={item}\r\n onClick={() => setPage(item)}\r\n className={clsx(\r\n \"min-w-8 px-2 py-1 rounded text-sm font-medium transition-colors\",\r\n item === safePage\r\n ? \"bg-blue-500 text-white\"\r\n : \"text-gray-600 hover:bg-gray-100\",\r\n )}\r\n >\r\n {item}\r\n </button>\r\n ),\r\n )}\r\n\r\n <button\r\n onClick={() => setPage((p) => Math.min(totalPages, p + 1))}\r\n disabled={safePage >= totalPages}\r\n className={clsx(\r\n \"p-1.5 rounded transition-colors\",\r\n safePage >= totalPages\r\n ? \"text-gray-300 cursor-not-allowed\"\r\n : \"text-gray-600 hover:bg-gray-100\",\r\n )}\r\n >\r\n <ChevronRight className=\"w-4 h-4\" />\r\n </button>\r\n </div>\r\n\r\n <div className=\"text-gray-500\">\r\n Page {safePage} sur {totalPages}\r\n </div>\r\n </div>\r\n )}\r\n\r\n {tooltip && (\r\n <div\r\n className=\"fixed z-20 px-3 py-2 text-sm text-white bg-gray-800 rounded-lg shadow-lg pointer-events-none whitespace-nowrap\"\r\n style={{\r\n left: tooltip.x,\r\n top: tooltip.y - 8,\r\n transform: \"translate(-50%, -100%)\",\r\n }}\r\n >\r\n {tooltip.content}\r\n </div>\r\n )}\r\n <style>{`\r\n @media print {\r\n body * { visibility: hidden; }\r\n .w-full.overflow-x-auto { visibility: visible; }\r\n .w-full.overflow-x-auto * { visibility: visible; }\r\n .w-full.overflow-x-auto { position: absolute; left: 0; top: 0; width: 100%; }\r\n }\r\n `}</style>\r\n </div>\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport { X } from \"lucide-react\";\r\nimport { ApiError } from \"../../../utils/src\";\r\nimport { useState } from \"react\";\r\n\r\ninterface ErrorDisplayProps {\r\n error: ApiError | null;\r\n}\r\n\r\nexport function ErrorDisplay({ error }: ErrorDisplayProps) {\r\n const [dismissed, setDismissed] = useState(false);\r\n\r\n if (!error || dismissed) return null;\r\n\r\n return (\r\n <div className=\"w-full overflow-x-auto\">\r\n <div className=\"rounded-lg shadow-md border border-red-200 bg-red-50\">\r\n <div className=\"flex items-start justify-between gap-4 px-4 py-4\">\r\n <div className=\"flex flex-col gap-1\">\r\n <p className=\"text-red-700 font-medium\">Erreur</p>\r\n <p className=\"text-red-600 text-sm\">{error.message}</p>\r\n </div>\r\n <button\r\n onClick={() => setDismissed(true)}\r\n className=\"text-red-400 hover:text-red-600 shrink-0 cursor-pointer\"\r\n >\r\n <X className=\"w-5 h-5\" />\r\n </button>\r\n </div>\r\n </div>\r\n </div>\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport React, { useState, useRef, useEffect } from \"react\";\r\nimport { Ellipsis } from \"lucide-react\";\r\n\r\nexport type TableAction<T> = {\r\n label: string;\r\n icon: React.ReactNode;\r\n callback: (row: T) => void;\r\n color?: string;\r\n};\r\n\r\ntype ActionsMenuProps<T> = {\r\n row: T;\r\n actions: TableAction<T>[];\r\n};\r\n\r\nexport function ActionsMenu<T>({ row, actions }: ActionsMenuProps<T>) {\r\n const [isOpen, setIsOpen] = useState(false);\r\n const [coords, setCoords] = useState({ top: 0, left: 0 });\r\n const buttonRef = useRef<HTMLButtonElement>(null);\r\n const menuRef = useRef<HTMLDivElement>(null);\r\n\r\n // Fermer le menu si clic en dehors\r\n useEffect(() => {\r\n function handleClickOutside(event: MouseEvent) {\r\n if (\r\n menuRef.current &&\r\n buttonRef.current &&\r\n !menuRef.current.contains(event.target as Node) &&\r\n !buttonRef.current.contains(event.target as Node)\r\n ) {\r\n setIsOpen(false);\r\n }\r\n }\r\n\r\n document.addEventListener(\"mousedown\", handleClickOutside);\r\n return () => document.removeEventListener(\"mousedown\", handleClickOutside);\r\n }, []);\r\n\r\n const toggleMenu = () => {\r\n if (buttonRef.current) {\r\n const rect = buttonRef.current.getBoundingClientRect();\r\n const menuWidth = 180;\r\n const menuHeight = actions.length * 40;\r\n\r\n const spaceBelow = window.innerHeight - rect.bottom;\r\n const spaceRight = window.innerWidth - rect.left;\r\n\r\n let top = rect.bottom;\r\n let left = rect.left;\r\n\r\n // If not enough space below, show above\r\n if (spaceBelow < menuHeight + 20) {\r\n top = rect.top - menuHeight;\r\n }\r\n\r\n // If not enough space on the right, align to the left\r\n if (spaceRight < menuWidth + 20) {\r\n left = rect.left - menuWidth + 30;\r\n }\r\n\r\n setCoords({ top, left });\r\n }\r\n setIsOpen(!isOpen);\r\n };\r\n\r\n return (\r\n <>\r\n <button\r\n ref={buttonRef}\r\n onClick={toggleMenu}\r\n className=\"p-1 hover:bg-gray-100 rounded-full\"\r\n >\r\n <Ellipsis className=\"w-5 h-5\" />\r\n </button>\r\n\r\n {isOpen && (\r\n <div\r\n ref={menuRef}\r\n className=\"fixed bg-white border border-gray-200 rounded shadow-lg z-20\"\r\n style={{\r\n top: coords.top,\r\n left: coords.left,\r\n minWidth: 180,\r\n }}\r\n >\r\n {actions.map((action, idx) => (\r\n <button\r\n key={idx}\r\n className={`flex items-center gap-2 px-4 py-2 w-full text-sm hover:bg-gray-100 ${\r\n action.color || \"text-gray-700\"\r\n }`}\r\n onClick={() => {\r\n action.callback(row);\r\n setIsOpen(false);\r\n }}\r\n >\r\n {action.icon}\r\n {action.label}\r\n </button>\r\n ))}\r\n </div>\r\n )}\r\n </>\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport { X } from \"lucide-react\";\r\nimport React, { useEffect } from \"react\";\r\nimport { createPortal } from \"react-dom\";\r\n\r\ntype ModalProps = {\r\n title: string;\r\n isOpen: boolean;\r\n onClose: () => void;\r\n children: React.ReactNode | ((requestClose: () => void) => React.ReactNode);\r\n};\r\n\r\nexport function Modal({ title, isOpen, onClose, children }: ModalProps) {\r\n const requestClose = () => {\r\n onClose();\r\n };\r\n\r\n useEffect(() => {\r\n if (isOpen) {\r\n document.body.style.overflow = \"hidden\";\r\n }\r\n\r\n return () => {\r\n document.body.style.overflow = \"\";\r\n };\r\n }, [isOpen]);\r\n\r\n useEffect(() => {\r\n function handleEsc(e: KeyboardEvent) {\r\n if (e.key === \"Escape\") {\r\n onClose();\r\n }\r\n }\r\n\r\n if (isOpen) {\r\n document.addEventListener(\"keydown\", handleEsc);\r\n }\r\n\r\n return () => {\r\n document.removeEventListener(\"keydown\", handleEsc);\r\n };\r\n }, [isOpen, onClose]);\r\n\r\n if (!isOpen) return null;\r\n\r\n const content =\r\n typeof children === \"function\" ? children(requestClose) : children;\r\n\r\n return createPortal(\r\n <div className=\"fixed inset-0 z-50 flex items-center justify-center\">\r\n <div\r\n className=\"absolute inset-0 bg-black/20 backdrop-blur-sm\"\r\n onClick={onClose}\r\n />\r\n\r\n <div className=\"relative bg-white rounded-lg shadow-lg w-full max-w-2xl mx-4 p-6 flex flex-col max-h-[85vh]\">\r\n <div className=\"flex items-center justify-between mb-4 border-b-2 border-gray-400 pb-3 sticky top-0 bg-white z-10\">\r\n <h2 className=\"text-lg font-semibold text-gray-900\">{title}</h2>\r\n\r\n <button\r\n onClick={onClose}\r\n className=\"text-gray-500 hover:text-gray-700 text-xl cursor-pointer\"\r\n >\r\n <X />\r\n </button>\r\n </div>\r\n\r\n <div className=\"overflow-y-auto flex-1 min-h-0\">{content}</div>\r\n </div>\r\n </div>,\r\n document.body,\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport { useCallback, useEffect, useRef, useState } from \"react\";\r\nimport { ApiError } from \"../../../utils/src/fetcher\";\r\nimport { CircleQuestionMark } from \"lucide-react\";\r\n\r\nconst ERROR_COUNTDOWN = 10;\r\n\r\ninterface ConfirmationProps {\r\n question: string;\r\n messageYes: string;\r\n messageNo: string;\r\n requestClose: () => void;\r\n onAction: () =>\r\n | void\r\n | Promise<void>\r\n | Promise<boolean>\r\n | Promise<{ success: true }>;\r\n isProcessing: boolean;\r\n error: ApiError | null;\r\n resetRequest: () => void;\r\n}\r\n\r\nexport function Confirmation({\r\n question,\r\n messageYes,\r\n messageNo,\r\n requestClose,\r\n onAction,\r\n isProcessing,\r\n error,\r\n resetRequest,\r\n}: ConfirmationProps) {\r\n const [countdown, setCountdown] = useState(0);\r\n const countdownRef = useRef<number | null>(null);\r\n const resetRequestRef = useRef(resetRequest);\r\n\r\n useEffect(() => {\r\n resetRequestRef.current = resetRequest;\r\n }, [resetRequest]);\r\n\r\n const clearCountdown = useCallback(() => {\r\n if (countdownRef.current !== null) {\r\n window.clearInterval(countdownRef.current);\r\n countdownRef.current = null;\r\n }\r\n }, []);\r\n\r\n const resetConfirmationState = useCallback(() => {\r\n clearCountdown();\r\n setCountdown(0);\r\n }, [clearCountdown]);\r\n\r\n const handleResetRequest = useCallback(() => {\r\n resetConfirmationState();\r\n resetRequest();\r\n }, [resetConfirmationState, resetRequest]);\r\n\r\n const handleRequestClose = useCallback(() => {\r\n resetConfirmationState();\r\n resetRequest();\r\n requestClose();\r\n }, [requestClose, resetConfirmationState, resetRequest]);\r\n\r\n const handleAction = useCallback(async () => {\r\n try {\r\n await onAction();\r\n handleRequestClose();\r\n } catch {\r\n // L'erreur est propagée par le parent via la prop `error`.\r\n }\r\n }, [handleRequestClose, onAction]);\r\n\r\n useEffect(() => {\r\n clearCountdown();\r\n\r\n if (!error) {\r\n const resetTimeoutId = window.setTimeout(() => {\r\n setCountdown(0);\r\n }, 0);\r\n\r\n return () => {\r\n window.clearTimeout(resetTimeoutId);\r\n };\r\n }\r\n\r\n const startCountdownTimeoutId = window.setTimeout(() => {\r\n setCountdown(ERROR_COUNTDOWN);\r\n\r\n countdownRef.current = window.setInterval(() => {\r\n setCountdown((previousCountdown) => {\r\n if (previousCountdown <= 1) {\r\n clearCountdown();\r\n window.setTimeout(() => {\r\n resetRequestRef.current();\r\n }, 0);\r\n\r\n return 0;\r\n }\r\n\r\n return previousCountdown - 1;\r\n });\r\n }, 1000);\r\n }, 0);\r\n\r\n return () => {\r\n window.clearTimeout(startCountdownTimeoutId);\r\n clearCountdown();\r\n };\r\n }, [clearCountdown, error]);\r\n\r\n useEffect(() => {\r\n return () => {\r\n clearCountdown();\r\n resetRequestRef.current();\r\n };\r\n }, [clearCountdown]);\r\n\r\n const isErrorVisible = Boolean(error) && countdown > 0;\r\n\r\n if (!question) return null;\r\n\r\n return (\r\n <div className=\"flex flex-col items-center gap-3 z-40\">\r\n <CircleQuestionMark className=\"text-red-500 text-5xl\" />\r\n <h2 className=\"text-xl font-bold text-red-500\">Confirmation requise</h2>\r\n\r\n <p className=\"mt-4 text-md leading-relaxed text-gray-700\">{question}</p>\r\n\r\n <div className=\"mt-6 flex w-full gap-3\">\r\n <button\r\n type=\"button\"\r\n onClick={handleRequestClose}\r\n disabled={isProcessing}\r\n className=\"w-full rounded-lg border border-gray-300 bg-white px-4 py-2 text-sm font-semibold text-gray-700 transition hover:cursor-pointer hover:bg-gray-100 disabled:cursor-not-allowed disabled:opacity-50 disabled:hover:bg-white\"\r\n >\r\n {messageNo}\r\n </button>\r\n\r\n <button\r\n type=\"button\"\r\n onClick={handleAction}\r\n disabled={isProcessing}\r\n className=\"w-full rounded-lg bg-red-400 px-4 py-2 text-sm font-semibold text-white transition hover:cursor-pointer hover:bg-red-500 active:scale-95 disabled:opacity-50 disabled:hover:bg-red-500\"\r\n >\r\n {isProcessing ? \"operation en cours\" : messageYes}\r\n </button>\r\n </div>\r\n\r\n {error && isErrorVisible && (\r\n <div className=\"mt-4 w-full rounded-lg border border-red-200 bg-red-50 p-4 text-left text-sm text-red-700\">\r\n <div className=\"flex items-start justify-between gap-3\">\r\n <div>\r\n <p className=\"font-semibold\">Erreur</p>\r\n <p className=\"mt-1 text-sm\">{error.message}</p>\r\n </div>\r\n\r\n <button\r\n type=\"button\"\r\n onClick={handleResetRequest}\r\n className=\"rounded-full bg-red-100 px-2 py-1 text-xs font-semibold text-red-700 hover:bg-red-200\"\r\n >\r\n Fermer\r\n </button>\r\n </div>\r\n\r\n <p className=\"mt-3 text-xs text-red-600\">\r\n Ce message disparait dans {countdown}s...\r\n </p>\r\n </div>\r\n )}\r\n </div>\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport React from \"react\";\r\n\r\ntype HeaderContentProps = {\r\n title: string;\r\n description: string;\r\n\r\n actionLabel?: string;\r\n onAction?: () => void;\r\n icon?: React.ReactNode;\r\n};\r\n\r\nexport function HeaderContent({\r\n title,\r\n description,\r\n actionLabel,\r\n onAction,\r\n icon,\r\n}: HeaderContentProps) {\r\n return (\r\n <div className=\"flex flex-col md:flex-row md:items-center md:justify-between gap-4 mb-6\">\r\n <div>\r\n <h1 className=\"text-xl font-semibold text-gray-900 flex items-center gap-2\">\r\n {title}\r\n </h1>\r\n\r\n {description && (\r\n <p className=\"text-sm text-gray-500 mt-1\">{description}</p>\r\n )}\r\n </div>\r\n\r\n {actionLabel && onAction && (\r\n <button\r\n onClick={onAction}\r\n className=\"font-semibold md:inline-flex items-center gap-2 bg-gray-900 text-white px-4 py-2 rounded-md text-sm hover:bg-gray-700 transition hover:cursor-pointer\"\r\n >\r\n {icon && <span className=\"w-4 h-4\">{icon}</span>}\r\n {actionLabel}\r\n </button>\r\n )}\r\n </div>\r\n );\r\n}\r\n\r\n","import React, { useState, useEffect, useRef, useCallback } from \"react\";\r\nimport { ApiError } from \"../../../utils/src/fetcher\";\r\nimport { X } from \"lucide-react\";\r\n\r\ninterface FormProps extends React.FormHTMLAttributes<HTMLFormElement> {\r\n erreurs?: ApiError | null;\r\n onErrorClose?: () => void;\r\n}\r\n\r\nconst Form: React.FC<FormProps> = ({\r\n erreurs,\r\n onErrorClose,\r\n children,\r\n className,\r\n ...props\r\n}) => {\r\n const formClassName = [\"flex flex-col gap-3\", className]\r\n .filter(Boolean)\r\n .join(\" \");\r\n const errorMessage = erreurs?.message || null;\r\n const [showError, setShowError] = useState(!!erreurs);\r\n const [countdown, setCountdown] = useState(erreurs ? 10 : 0);\r\n const [animating, setAnimating] = useState(!!erreurs);\r\n const intervalRef = useRef<number | null>(null);\r\n const hasClosedRef = useRef(false);\r\n\r\n const closeError = useCallback(\r\n (triggerCallback = true) => {\r\n if (intervalRef.current !== null) {\r\n window.clearInterval(intervalRef.current);\r\n intervalRef.current = null;\r\n }\r\n\r\n setShowError(false);\r\n setAnimating(false);\r\n setCountdown(0);\r\n\r\n if (triggerCallback && onErrorClose && !hasClosedRef.current) {\r\n hasClosedRef.current = true;\r\n onErrorClose();\r\n }\r\n },\r\n [onErrorClose],\r\n );\r\n\r\n useEffect(() => {\r\n hasClosedRef.current = false;\r\n\r\n if (!erreurs) {\r\n const closeTimeout = window.setTimeout(() => closeError(false), 0);\r\n return () => {\r\n window.clearTimeout(closeTimeout);\r\n };\r\n }\r\n\r\n const initTimeout = window.setTimeout(() => {\r\n setShowError(true);\r\n setAnimating(true);\r\n setCountdown(10);\r\n }, 0);\r\n\r\n intervalRef.current = window.setInterval(() => {\r\n setCountdown((prev) => {\r\n if (prev <= 1) {\r\n closeError(true);\r\n return 0;\r\n }\r\n return prev - 1;\r\n });\r\n }, 1000);\r\n\r\n return () => {\r\n window.clearTimeout(initTimeout);\r\n if (intervalRef.current !== null) {\r\n window.clearInterval(intervalRef.current);\r\n intervalRef.current = null;\r\n }\r\n };\r\n }, [erreurs, closeError]);\r\n\r\n return (\r\n <>\r\n <form className={formClassName} {...props}>\r\n {children}\r\n </form>\r\n {showError && errorMessage && (\r\n <div\r\n className={`fixed top-0 left-0 right-0 z-[9999] bg-red-500 text-white p-4 rounded-b-md shadow-lg flex justify-between items-center transition-transform duration-300 ${\r\n animating\r\n ? \"transform translate-y-0\"\r\n : \"transform -translate-y-full\"\r\n }`}\r\n >\r\n <span>{errorMessage}</span>\r\n <div className=\"flex items-center\">\r\n <span className=\"mr-2\">{countdown}s</span>\r\n <button onClick={() => closeError(true)}>\r\n <X size={20} />\r\n </button>\r\n </div>\r\n </div>\r\n )}\r\n </>\r\n );\r\n};\r\n\r\nexport { Form };\r\n","import React from \"react\";\r\n\r\ninterface FieldContainerProps {\r\n children: React.ReactNode;\r\n className?: string;\r\n}\r\n\r\nexport function FieldContainer({ children, className }: FieldContainerProps) {\r\n return (\r\n <div className={`flex flex-col gap-2 mb-3 relative ${className ?? \"\"}`}>\r\n <div className=\"flex flex-col gap-1\">{children}</div>\r\n </div>\r\n );\r\n}\r\n","import React from \"react\";\r\n\r\ninterface LabelProps extends Omit<\r\n React.LabelHTMLAttributes<HTMLLabelElement>,\r\n \"required\"\r\n> {\r\n required?: boolean;\r\n}\r\n\r\nconst Label = React.forwardRef<HTMLLabelElement, LabelProps>(\r\n ({ required, children, className, ...props }, ref) => {\r\n return (\r\n <label\r\n ref={ref}\r\n className={`font-semibold text-gray-600 block ${className ?? \"\"}`.trim()}\r\n {...props}\r\n >\r\n {children}\r\n {required ? <span className=\"text-red-500 ml-1\">*</span> : null}\r\n </label>\r\n );\r\n },\r\n);\r\n\r\nLabel.displayName = \"Label\";\r\n\r\nexport { Label };\r\n","import React, { useState } from \"react\";\r\nimport { Eye, EyeOff } from \"lucide-react\";\r\n\r\nconst Input = React.forwardRef<\r\n HTMLInputElement,\r\n React.InputHTMLAttributes<HTMLInputElement>\r\n>(({ type, className, ...props }, ref) => {\r\n const [showPassword, setShowPassword] = useState(false);\r\n\r\n const isPassword = type === \"password\";\r\n const inputType = isPassword ? (showPassword ? \"text\" : \"password\") : type;\r\n\r\n return (\r\n <div className=\"relative\">\r\n <input\r\n ref={ref}\r\n type={inputType}\r\n className={`w-full px-3 py-2 pr-10 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-gray-500 focus:border-transparent transition duration-200 ${className || \"\"}`}\r\n {...props}\r\n />\r\n {isPassword && (\r\n <button\r\n type=\"button\"\r\n onClick={() => setShowPassword(!showPassword)}\r\n className=\"absolute inset-y-0 right-0 pr-3 flex items-center text-gray-500 hover:text-gray-700\"\r\n >\r\n {showPassword ? <EyeOff size={20} /> : <Eye size={20} />}\r\n </button>\r\n )}\r\n </div>\r\n );\r\n});\r\n\r\nInput.displayName = \"Input\";\r\n\r\nexport { Input };\r\n","import React from \"react\";\r\n\r\nconst Select = React.forwardRef<\r\n HTMLSelectElement,\r\n React.SelectHTMLAttributes<HTMLSelectElement>\r\n>(({ className, ...props }, ref) => {\r\n return (\r\n <select\r\n ref={ref}\r\n className={`w-full px-3 py-2 pr-10 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-gray-500 focus:border-transparent transition duration-200 bg-white cursor-pointer appearance-none bg-no-repeat bg-right bg-contain ${className || \"\"}`}\r\n style={{\r\n backgroundImage: `url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' fill='none' viewBox='0 0 20 20'%3e%3cpath stroke='%236b7280' stroke-linecap='round' stroke-linejoin='round' stroke-width='1.5' d='m6 8 4 4 4-4'/%3e%3c/svg%3e\")`,\r\n backgroundPosition: \"right 0.75rem center\",\r\n backgroundSize: \"1.25em 1.25em\",\r\n }}\r\n {...props}\r\n />\r\n );\r\n});\r\n\r\nSelect.displayName = \"Select\";\r\n\r\nexport { Select };\r\n\r\n// Option Component\r\n\r\nconst Option = React.forwardRef<\r\n HTMLOptionElement,\r\n React.OptionHTMLAttributes<HTMLOptionElement>\r\n>(({ ...props }, ref) => {\r\n return <option ref={ref} {...props} />;\r\n});\r\n\r\nOption.displayName = \"Option\";\r\n\r\nexport { Option };\r\n","import React from \"react\";\r\n\r\nconst TextArea = React.forwardRef<\r\n HTMLTextAreaElement,\r\n React.TextareaHTMLAttributes<HTMLTextAreaElement>\r\n>(({ ...props }, ref) => {\r\n return (\r\n <textarea\r\n ref={ref}\r\n className=\"w-full px-3 py-2 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-gray-500 focus:border-transparent transition duration-200 resize-none\"\r\n {...props}\r\n />\r\n );\r\n});\r\n\r\nTextArea.displayName = \"TextArea\";\r\n\r\nexport { TextArea };\r\n","import React from \"react\";\r\n\r\nconst DatePicker = React.forwardRef<\r\n HTMLInputElement,\r\n React.InputHTMLAttributes<HTMLInputElement>\r\n>(({ className, placeholder, required, ...props }, ref) => {\r\n return (\r\n <div className=\"relative\">\r\n <input\r\n ref={ref}\r\n type=\"date\"\r\n required={required ?? true}\r\n className={`peer w-full px-3 py-2 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-gray-500 focus:border-transparent transition duration-200 ${className ?? \"\"}`}\r\n {...props}\r\n />\r\n <span className=\"absolute left-3 top-1/2 -translate-y-1/2 text-gray-400 pointer-events-none peer-valid:hidden md:hidden\">\r\n {placeholder ?? \"jj/mm/aaaa\"}\r\n </span>\r\n </div>\r\n );\r\n});\r\n\r\nDatePicker.displayName = \"DatePicker\";\r\n\r\nexport { DatePicker };\r\n","import { Loader } from \"lucide-react\";\r\n\r\ninterface LoadingProps {\r\n text: string;\r\n}\r\n\r\nexport function Loading(props: LoadingProps) {\r\n return (\r\n <div className=\"flex items-center justify-center\">\r\n <div className=\"flex flex-col items-center gap-4\">\r\n <Loader className=\"animate-spin\" size={40} />\r\n\r\n <p className=\"text-gray-600 text-md font-medium\">{props.text}</p>\r\n </div>\r\n </div>\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport { LoaderCircle } from \"lucide-react\";\r\n\r\ninterface LoaderSubmitProps {\r\n label: string;\r\n loadingLabel: string;\r\n isLoading: boolean;\r\n}\r\n\r\nexport function LoaderSubmit({ label, loadingLabel, isLoading }: LoaderSubmitProps) {\r\n return (\r\n <>\r\n {isLoading ? (\r\n <div className=\"flex flex-row gap-2 items-center\">\r\n <LoaderCircle className=\"animate-spin text-gray-500\" />\r\n <p className=\"text-gray-500 font-semibold\">{loadingLabel}</p>\r\n </div>\r\n ) : (\r\n <button\r\n type=\"submit\"\r\n className=\"bg-gray-900 text-white px-6 py-2 rounded-md hover:bg-gray-700 hover:cursor-pointer transition-colors duration-300 font-semibold shadow-md\"\r\n disabled={isLoading}\r\n >\r\n {label}\r\n </button>\r\n )}\r\n </>\r\n );\r\n}\r\n","\"use client\";\n\nimport { useRouter } from \"next/navigation\";\nimport { useEffect, useState } from \"react\";\n\ninterface SessionExpiredProps {\n redirectUrl?: string;\n}\n\nexport function SessionExpired({ redirectUrl = \"/\" }: SessionExpiredProps) {\n const router = useRouter();\n const [countdown, setCountdown] = useState(10);\n\n useEffect(() => {\n if (countdown <= 0) {\n router.push(redirectUrl);\n return;\n }\n const timer = setTimeout(() => setCountdown((c) => c - 1), 1000);\n return () => clearTimeout(timer);\n }, [countdown, router, redirectUrl]);\n\n const handleConnect = () => {\n router.push(redirectUrl);\n };\n\n return (\n <div className=\"min-h-screen flex items-center justify-center bg-gray-50\">\n <div className=\"max-w-md w-full text-center space-y-8 p-8\">\n <div className=\"space-y-3\">\n <div className=\"flex justify-center\">\n <svg\n className=\"w-16 h-16 text-gray-300\"\n fill=\"none\"\n viewBox=\"0 0 24 24\"\n stroke=\"currentColor\"\n strokeWidth={1.5}\n >\n <path\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n d=\"M16.5 10.5V6.75a4.5 4.5 0 10-9 0v3.75m-.75 11.25h10.5a2.25 2.25 0 002.25-2.25v-6.75a2.25 2.25 0 00-2.25-2.25H6.75a2.25 2.25 0 00-2.25 2.25v6.75a2.25 2.25 0 002.25 2.25z\"\n />\n </svg>\n </div>\n <h1 className=\"text-2xl font-semibold text-gray-900\">\n Session expirée\n </h1>\n <p className=\"text-gray-500\">\n Votre session a expiré ou vous n&apos;êtes pas connecté.\n Veuillez vous reconnecter pour accéder à cette page.\n </p>\n </div>\n\n <button\n onClick={handleConnect}\n className=\"bg-gray-900 text-white px-6 py-2.5 rounded-md text-sm font-semibold hover:bg-gray-700 transition-colors\"\n >\n Me connecter\n </button>\n\n <p className=\"text-sm text-gray-400\">\n Redirection automatique dans {countdown}s...\n </p>\n </div>\n </div>\n );\n}\n","\"use client\";\n\nimport Image from \"next/image\";\nimport Link from \"next/link\";\n\ninterface AccessDeniedProps {\n logo: string;\n redirectTo: string;\n textRedirection: string;\n}\n\nexport function AccessDenied({ logo, redirectTo, textRedirection }: AccessDeniedProps) {\n return (\n <main className=\"min-h-screen py-16 px-4 bg-gradient-to-b from-gray-100 to-white text-gray-900 flex items-center justify-center\">\n <div className=\"max-w-md mx-auto text-center\">\n <div className=\"flex justify-center mb-6\">\n <Image\n alt=\"Logo\"\n height={100}\n width={100}\n src={logo}\n />\n </div>\n\n <h1 className=\"text-2xl font-bold text-red-600 mb-4\">\n Accès refusé\n </h1>\n\n <p className=\"text-gray-500 mb-8\">\n Vous ne disposez pas des droits nécessaires pour accéder à cette page.\n </p>\n\n <Link\n href={redirectTo}\n className=\"inline-block px-6 py-3 bg-gray-900 text-white rounded-lg font-semibold hover:bg-gray-700 transition-colors\"\n >\n {textRedirection}\n </Link>\n </div>\n </main>\n );\n}\n","export class ApiError extends Error {\r\n public status: number;\r\n public code?: string;\r\n public data?: unknown;\r\n\r\n constructor(params: {\r\n message: string;\r\n status: number;\r\n code?: string;\r\n data?: unknown;\r\n }) {\r\n super(params.message);\r\n this.status = params.status;\r\n this.code = params.code;\r\n this.data = params.data;\r\n }\r\n}\r\n\r\ntype BackendErrorShape = {\r\n code?: string;\r\n status?: number;\r\n message?: string;\r\n};\r\n\r\nexport type FetcherOptions = RequestInit & {\r\n skipJsonParsing?: boolean;\r\n};\r\n\r\nexport async function fetcher<T = unknown>(\r\n url: string,\r\n options: FetcherOptions = {},\r\n): Promise<T> {\r\n const { headers, skipJsonParsing = false, ...rest } = options;\r\n\r\n const response = await fetch(url, {\r\n credentials: \"include\",\r\n headers: {\r\n \"Content-Type\": \"application/json\",\r\n ...headers,\r\n },\r\n ...rest,\r\n });\r\n\r\n let responseData: unknown = null;\r\n const contentType = response.headers.get(\"content-type\");\r\n\r\n if (!skipJsonParsing && contentType?.includes(\"application/json\")) {\r\n responseData = await response.json();\r\n }\r\n\r\n if (!response.ok) {\r\n const backendError = responseData as BackendErrorShape;\r\n\r\n throw new ApiError({\r\n message: backendError?.message || \"Une erreur est survenue\",\r\n status: backendError?.status || response.status,\r\n code: backendError?.code,\r\n data: responseData,\r\n });\r\n }\r\n\r\n return responseData as T;\r\n}\r\n","export class HttpError extends Error {\r\n status: number;\r\n code?: string;\r\n\r\n constructor(message: string, status = 400, code?: string) {\r\n super(message);\r\n\r\n this.name = \"HttpError\";\r\n this.status = status;\r\n this.code = code;\r\n\r\n Object.setPrototypeOf(this, HttpError.prototype);\r\n }\r\n}\r\n","import { HttpError } from \"./http-error\";\r\n\r\nconst GENERIC_MESSAGE = \"Erreur serveur\";\r\n\r\nfunction shouldShowDetails(showDetails?: boolean): boolean {\r\n return showDetails ?? process.env.NODE_ENV !== \"production\";\r\n}\r\n\r\nfunction sanitizedResponse(\r\n message: string,\r\n code: string,\r\n status: number,\r\n showDetails?: boolean,\r\n) {\r\n return Response.json(\r\n {\r\n message: showDetails ? message : GENERIC_MESSAGE,\r\n code: showDetails ? code : \"INTERNAL_ERROR\",\r\n status,\r\n },\r\n { status },\r\n );\r\n}\r\n\r\n/**\r\n * Transforme n'importe quelle erreur en réponse JSON standardisée\r\n * @param error L'erreur levée\r\n * @param defaultStatus Statut HTTP par défaut si non défini\r\n * @param showDetails Force l'affichage des détails (true) ou le mode sécurisé (false). Par défaut : automatique selon NODE_ENV\r\n * @returns Response JSON\r\n */\r\nexport function handleServerError(\r\n error: unknown,\r\n defaultStatus = 500,\r\n showDetails?: boolean,\r\n) {\r\n const details = shouldShowDetails(showDetails);\r\n\r\n console.error(\"Erreur capturée :\", error);\r\n\r\n // Cas HttpError personnalisé — toujours visible (erreur intentionnelle)\r\n if (error instanceof HttpError) {\r\n const status = error.status ?? defaultStatus;\r\n return Response.json(\r\n {\r\n message: error.message,\r\n code: error.code ?? \"INTERNAL_ERROR\",\r\n status,\r\n },\r\n { status },\r\n );\r\n }\r\n\r\n // Cas classique : objet Error\r\n if (error instanceof Error) {\r\n return sanitizedResponse(\r\n error.message,\r\n \"INTERNAL_ERROR\",\r\n defaultStatus,\r\n details,\r\n );\r\n }\r\n\r\n // Cas objet brut ou autre type\r\n if (typeof error === \"object\" && error !== null) {\r\n return sanitizedResponse(\r\n JSON.stringify(error),\r\n \"INTERNAL_ERROR\",\r\n defaultStatus,\r\n details,\r\n );\r\n }\r\n\r\n // Cas fallback : string ou autre\r\n return sanitizedResponse(\r\n String(error),\r\n \"INTERNAL_ERROR\",\r\n defaultStatus,\r\n details,\r\n );\r\n}\r\n","import { NextResponse } from \"next/server\";\r\nimport type { NextRequest } from \"next/server\";\r\nimport { jwtVerify } from \"jose\";\r\n\r\ninterface JwtPayload {\r\n id: string;\r\n role: string;\r\n permissions?: string[];\r\n}\r\n\r\ninterface AuthGuardOptions {\r\n publicRoutes: string[];\r\n loginUrl: string;\r\n jwtSecret: string;\r\n}\r\n\r\nexport async function authGuard(\r\n request: NextRequest,\r\n options: AuthGuardOptions,\r\n) {\r\n const { publicRoutes, loginUrl, jwtSecret } = options;\r\n\r\n if (!jwtSecret) {\r\n console.error(\"auth-guard: JWT_SECRET is not defined\");\r\n const loginUrlObj = new URL(loginUrl, request.url);\r\n loginUrlObj.searchParams.set(\"error\", \"authentification_requise\");\r\n return NextResponse.redirect(loginUrlObj);\r\n }\r\n\r\n const { pathname } = request.nextUrl;\r\n\r\n const isPublicRoute = publicRoutes.some((route) => {\r\n if (route.endsWith(\"/*\")) {\r\n return pathname.startsWith(route.slice(0, -2));\r\n }\r\n return pathname === route;\r\n });\r\n\r\n if (isPublicRoute) {\r\n return NextResponse.next();\r\n }\r\n\r\n const token = request.cookies.get(\"auth\")?.value;\r\n\r\n if (!token) {\r\n const loginUrlObj = new URL(loginUrl, request.url);\r\n loginUrlObj.searchParams.set(\"error\", \"authentification_requise\");\r\n return NextResponse.redirect(loginUrlObj);\r\n }\r\n\r\n let payload: JwtPayload;\r\n try {\r\n const secret = new TextEncoder().encode(jwtSecret);\r\n const result = await jwtVerify(token, secret, {\r\n algorithms: [\"HS256\"],\r\n });\r\n const rawPermissions = result.payload.permissions;\r\n payload = {\r\n id: String(result.payload.id || \"\"),\r\n role: String(result.payload.role || \"\"),\r\n permissions: Array.isArray(rawPermissions)\r\n ? (rawPermissions as string[])\r\n : [],\r\n };\r\n\r\n if (!payload.id || !payload.role) {\r\n const loginUrlObj = new URL(loginUrl, request.url);\r\n loginUrlObj.searchParams.set(\"error\", \"token_invalide\");\r\n return NextResponse.redirect(loginUrlObj);\r\n }\r\n } catch {\r\n const loginUrlObj = new URL(loginUrl, request.url);\r\n loginUrlObj.searchParams.set(\"error\", \"token_invalide\");\r\n return NextResponse.redirect(loginUrlObj);\r\n }\r\n\r\n const requestHeaders = new Headers(request.headers);\r\n requestHeaders.set(\"x-user-id\", payload.id);\r\n requestHeaders.set(\"x-user-role\", payload.role);\r\n requestHeaders.set(\r\n \"x-user-permissions\",\r\n (payload.permissions ?? []).join(\",\"),\r\n );\r\n\r\n return NextResponse.next({\r\n request: { headers: requestHeaders },\r\n });\r\n}\r\n"],"mappings":"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","names":["jsx","useState","useState","jsx","jsxs","jsx","jsxs","useState","useState","useEffect","jsx","jsxs","X","useEffect","jsx","jsxs","useCallback","useEffect","useRef","useState","jsx","jsxs","jsx","jsxs","useState","useEffect","useRef","useCallback","X","Fragment","jsx","jsxs","jsx","React","jsx","jsxs","React","useState","jsx","jsxs","React","jsx","React","jsx","React","jsx","React","jsx","jsxs","jsx","jsxs","Fragment","jsx","jsxs","useEffect","useState","jsx","jsxs","jsx","jsxs"]}
1
+ {"version":3,"sources":["../packages/ui/src/layouts/side-nav.tsx","../packages/ui/src/config/create-side-nav.tsx","../packages/ui/src/table/table.tsx","../packages/ui/src/feedback/error-display.tsx","../packages/ui/src/table/actions-menu.tsx","../packages/ui/src/modals/modal.tsx","../packages/ui/src/feedback/confirmation.tsx","../packages/ui/src/headers/header-content.tsx","../packages/ui/src/forms/form.tsx","../packages/ui/src/forms/field-container.tsx","../packages/ui/src/forms/label.tsx","../packages/ui/src/forms/input.tsx","../packages/ui/src/forms/select.tsx","../packages/ui/src/forms/textarea.tsx","../packages/ui/src/forms/date-picker.tsx","../packages/ui/src/loaders/loading.tsx","../packages/ui/src/loaders/loader-submit.tsx","../packages/ui/src/pages/session-expired.tsx","../packages/ui/src/pages/access-denied.tsx","../packages/ui/src/route-guard/route-guard.tsx","../packages/utils/src/fetcher.ts","../packages/lib/src/http-error.ts","../packages/lib/src/handle-server-error.ts","../packages/lib/src/auth-guard.ts"],"sourcesContent":["\"use client\";\r\n\r\nimport {\r\n ReactNode,\r\n useState,\r\n useEffect,\r\n createElement,\r\n isValidElement,\r\n type ComponentType,\r\n} from \"react\";\r\n\r\ntype IconType = ReactNode | ComponentType<{ size?: number }>;\r\n\r\nexport interface NavItem {\r\n id: string;\r\n label: string;\r\n title?: string;\r\n icon?: IconType;\r\n href: string;\r\n subItems?: NavItem[];\r\n}\r\n\r\nexport interface SideNavStaticConfig {\r\n brand?: {\r\n logo?: ReactNode;\r\n name?: string;\r\n tagline?: string;\r\n };\r\n mainItems: NavItem[];\r\n title?: string;\r\n footer?: { icon?: IconType; label: string; href: string }[];\r\n toggleIcon?: ReactNode;\r\n}\r\n\r\nexport interface SideNavProps extends SideNavStaticConfig {\r\n children: ReactNode;\r\n currentPath: string;\r\n}\r\n\r\nfunction isActive(href: string, currentPath: string) {\r\n return currentPath === href || currentPath.startsWith(href + \"/\");\r\n}\r\n\r\nfunction isExactActive(href: string, currentPath: string) {\r\n return currentPath === href;\r\n}\r\n\r\nexport function SideNav({\r\n children,\r\n title,\r\n mainItems,\r\n currentPath,\r\n brand,\r\n footer,\r\n toggleIcon,\r\n}: SideNavProps) {\r\n const activeMain = mainItems.find((item) => isActive(item.href, currentPath));\r\n const headerTitle = title ?? activeMain?.title ?? activeMain?.label;\r\n const [expandedSection, setExpandedSection] = useState<string | null>(\r\n activeMain?.id ?? null,\r\n );\r\n\r\n const toggleSection = (id: string) => {\r\n setExpandedSection((prev) => (prev === id ? null : id));\r\n };\r\n\r\n const [isMobileOpen, setIsMobileOpen] = useState(false);\r\n\r\n useEffect(() => {\r\n const handleEscape = (e: KeyboardEvent) => {\r\n if (e.key === \"Escape\") setIsMobileOpen(false);\r\n };\r\n document.addEventListener(\"keydown\", handleEscape);\r\n return () => document.removeEventListener(\"keydown\", handleEscape);\r\n }, []);\r\n\r\n useEffect(() => {\r\n if (isMobileOpen) {\r\n document.body.style.overflow = \"hidden\";\r\n } else {\r\n document.body.style.overflow = \"\";\r\n }\r\n return () => {\r\n document.body.style.overflow = \"\";\r\n };\r\n }, [isMobileOpen]);\r\n\r\n const closeMobileNav = () => setIsMobileOpen(false);\r\n\r\n return (\r\n <div className=\"flex min-h-screen\">\r\n <aside\r\n className={`w-64 bg-white border-r border-gray-200 flex flex-col fixed h-full z-50 transition-transform duration-300 ease-in-out md:translate-x-0 ${\r\n isMobileOpen ? \"translate-x-0\" : \"-translate-x-full\"\r\n }`}\r\n >\r\n {brand && (\r\n <div className=\"p-[6.5px] border-b border-gray-100\">\r\n <div className=\"flex flex-row gap-2 items-center\">\r\n {brand.logo &&\r\n (typeof brand.logo === \"string\" ? (\r\n <img\r\n src={brand.logo}\r\n alt={brand.name ?? \"\"}\r\n className=\"w-12.5 h-12.5\"\r\n />\r\n ) : (\r\n brand.logo\r\n ))}\r\n {brand.name && (\r\n <p className=\"text-gray-500 text-base font-semibold\">\r\n {brand.name}\r\n </p>\r\n )}\r\n </div>\r\n </div>\r\n )}\r\n\r\n <nav className=\"flex-1 p-4 overflow-y-auto\">\r\n <ul className=\"space-y-1\">\r\n {mainItems.map((item) => {\r\n const active = isActive(item.href, currentPath);\r\n const isExpanded = expandedSection === item.id;\r\n const hasSubItems = item.subItems && item.subItems.length > 0;\r\n\r\n return (\r\n <li key={item.id}>\r\n <div className=\"flex items-center gap-1\">\r\n <a\r\n href={item.href}\r\n onClick={closeMobileNav}\r\n className={`flex items-center gap-3 px-3 py-2.5 rounded-lg text-sm font-medium transition-colors flex-1 ${\r\n active\r\n ? \"bg-gray-200 text-black\"\r\n : \"text-gray-500 hover:bg-gray-100\"\r\n }`}\r\n >\r\n {item.icon &&\r\n (typeof item.icon === \"string\" ? (\r\n <span className=\"text-lg\">{item.icon}</span>\r\n ) : isValidElement(item.icon) ? (\r\n item.icon\r\n ) : (\r\n createElement(\r\n item.icon as ComponentType<{ size?: number }>,\r\n { size: 20 },\r\n )\r\n ))}\r\n {item.label}\r\n </a>\r\n {active && hasSubItems && (\r\n <button\r\n onClick={() => toggleSection(item.id)}\r\n className={`p-1.5 rounded-lg transition-colors ${\r\n active\r\n ? \"text-black hover:bg-gray-100\"\r\n : \"text-gray-500 hover:bg-gray-100\"\r\n }`}\r\n title={isExpanded ? \"Réduire\" : \"Développer\"}\r\n >\r\n {toggleIcon ? (\r\n <span\r\n className={`inline-block transition-transform duration-200 ${\r\n isExpanded ? \"rotate-0\" : \"-rotate-90\"\r\n }`}\r\n >\r\n {toggleIcon}\r\n </span>\r\n ) : (\r\n <span className=\"text-xs\">\r\n {isExpanded ? \"▼\" : \"▶\"}\r\n </span>\r\n )}\r\n </button>\r\n )}\r\n </div>\r\n\r\n {active && hasSubItems && (\r\n <div\r\n className={`grid transition-all duration-300 ease-in-out ${\r\n isExpanded ? \"grid-rows-[1fr]\" : \"grid-rows-[0fr]\"\r\n }`}\r\n >\r\n <div className=\"overflow-hidden\">\r\n <ul className=\"ml-4 mt-1 space-y-1 pl-2\">\r\n {item.subItems!.map((sub) => (\r\n <li key={sub.id}>\r\n <a\r\n href={sub.href}\r\n onClick={closeMobileNav}\r\n className={`flex items-center gap-2 px-3 py-2 rounded-lg text-sm font-medium transition-colors ${\r\n isExactActive(sub.href, currentPath)\r\n ? \"bg-gray-200 text-black\"\r\n : \"text-gray-500 hover:bg-gray-100\"\r\n }`}\r\n >\r\n {sub.label}\r\n </a>\r\n </li>\r\n ))}\r\n </ul>\r\n </div>\r\n </div>\r\n )}\r\n </li>\r\n );\r\n })}\r\n </ul>\r\n </nav>\r\n\r\n {footer && footer.length > 0 && (\r\n <div className=\"p-4 border-t border-gray-100 space-y-1\">\r\n {footer.map((item) => (\r\n <a\r\n key={item.label}\r\n href={item.href}\r\n onClick={closeMobileNav}\r\n className=\"flex items-center gap-3 px-3 py-2.5 rounded-lg text-sm font-medium text-gray-700 hover:bg-gray-100 transition-colors\"\r\n >\r\n {typeof item.icon === \"string\" ? (\r\n <span className=\"text-lg\">{item.icon}</span>\r\n ) : isValidElement(item.icon) ? (\r\n item.icon\r\n ) : (\r\n createElement(item.icon as ComponentType<{ size?: number }>, {\r\n size: 20,\r\n })\r\n )}\r\n {item.label}\r\n </a>\r\n ))}\r\n </div>\r\n )}\r\n </aside>\r\n\r\n {isMobileOpen && (\r\n <div\r\n className=\"fixed inset-0 z-40 bg-black/50 md:hidden\"\r\n onClick={closeMobileNav}\r\n aria-hidden=\"true\"\r\n />\r\n )}\r\n\r\n <div className=\"flex-1 ml-64 max-md:ml-0 min-w-0\">\r\n {headerTitle && (\r\n <header className=\"h-16 bg-white border-b border-gray-200 flex items-center justify-between px-6 fixed top-0 right-0 left-64 max-md:left-0 z-20\">\r\n <div className=\"flex items-center gap-2\">\r\n <button\r\n className=\"md:hidden p-2 -ml-2 rounded-lg hover:bg-gray-100 transition-colors\"\r\n onClick={() => setIsMobileOpen(!isMobileOpen)}\r\n aria-label={isMobileOpen ? \"Fermer le menu\" : \"Menu\"}\r\n aria-expanded={isMobileOpen}\r\n >\r\n {isMobileOpen ? (\r\n <svg\r\n className=\"w-5 h-5\"\r\n fill=\"none\"\r\n viewBox=\"0 0 24 24\"\r\n stroke=\"currentColor\"\r\n strokeWidth={2}\r\n >\r\n <path\r\n strokeLinecap=\"round\"\r\n strokeLinejoin=\"round\"\r\n d=\"M6 18L18 6M6 6l12 12\"\r\n />\r\n </svg>\r\n ) : (\r\n <svg\r\n className=\"w-5 h-5\"\r\n fill=\"none\"\r\n viewBox=\"0 0 24 24\"\r\n stroke=\"currentColor\"\r\n strokeWidth={2}\r\n >\r\n <path\r\n strokeLinecap=\"round\"\r\n strokeLinejoin=\"round\"\r\n d=\"M4 6h16M4 12h16M4 18h16\"\r\n />\r\n </svg>\r\n )}\r\n </button>\r\n <h1 className=\"text-base font-semibold text-gray-500\">\r\n {headerTitle}\r\n </h1>\r\n </div>\r\n {brand?.tagline && (\r\n <span className=\"text-sm text-gray-500 max-md:hidden\">\r\n {brand.tagline}\r\n </span>\r\n )}\r\n </header>\r\n )}\r\n {!headerTitle && (\r\n <button\r\n className=\"md:hidden fixed top-4 left-4 z-10 p-2 rounded-lg bg-white border border-gray-200 shadow-sm hover:bg-gray-100 transition-colors\"\r\n onClick={() => setIsMobileOpen(!isMobileOpen)}\r\n aria-label={isMobileOpen ? \"Fermer le menu\" : \"Menu\"}\r\n aria-expanded={isMobileOpen}\r\n >\r\n {isMobileOpen ? (\r\n <svg\r\n className=\"w-5 h-5\"\r\n fill=\"none\"\r\n viewBox=\"0 0 24 24\"\r\n stroke=\"currentColor\"\r\n strokeWidth={2}\r\n >\r\n <path\r\n strokeLinecap=\"round\"\r\n strokeLinejoin=\"round\"\r\n d=\"M6 18L18 6M6 6l12 12\"\r\n />\r\n </svg>\r\n ) : (\r\n <svg\r\n className=\"w-5 h-5\"\r\n fill=\"none\"\r\n viewBox=\"0 0 24 24\"\r\n stroke=\"currentColor\"\r\n strokeWidth={2}\r\n >\r\n <path\r\n strokeLinecap=\"round\"\r\n strokeLinejoin=\"round\"\r\n d=\"M4 6h16M4 12h16M4 18h16\"\r\n />\r\n </svg>\r\n )}\r\n </button>\r\n )}\r\n <main\r\n className={(headerTitle ? \"p-6 pt-20\" : \"p-6\") + \" overflow-x-auto\"}\r\n >\r\n {children}\r\n </main>\r\n </div>\r\n </div>\r\n );\r\n}\r\n","import { SideNav, type SideNavStaticConfig } from \"../layouts/side-nav\";\n\nexport function createSideNav(config: SideNavStaticConfig) {\n return function ConfiguredSideNav({\n children,\n currentPath,\n }: {\n children: React.ReactNode;\n currentPath: string;\n }) {\n return (\n <SideNav {...config} currentPath={currentPath}>\n {children}\n </SideNav>\n );\n };\n}\n","\"use client\";\r\n\r\nimport { Printer, ChevronLeft, ChevronRight } from \"lucide-react\";\r\nimport clsx from \"clsx\";\r\nimport { useState, useMemo, useCallback } from \"react\";\r\nimport { ErrorDisplay } from \"../feedback/error-display\";\r\nimport { ApiError } from \"../../../utils/src/fetcher\";\r\n\r\nexport type Column<T> = {\r\n header: string;\r\n accessor?: keyof T;\r\n render?: (row: T) => React.ReactNode;\r\n excludeFromPrint?: boolean;\r\n};\r\n\r\ntype TableProps<T> = {\r\n data: T[];\r\n columns: Column<T>[];\r\n loading?: boolean;\r\n error?: ApiError | null;\r\n label?: string;\r\n printable?: boolean;\r\n pageSize?: number;\r\n pageSizeOptions?: number[];\r\n showPagination?: boolean;\r\n};\r\n\r\nconst VISIBLE_PAGES = 5;\r\n\r\nexport function Table<T>({\r\n data,\r\n columns,\r\n loading,\r\n error,\r\n label,\r\n printable,\r\n pageSize = 5,\r\n pageSizeOptions = [5, 10, 20],\r\n showPagination = true,\r\n}: TableProps<T>) {\r\n const [tooltip, setTooltip] = useState<{\r\n content: string;\r\n x: number;\r\n y: number;\r\n } | null>(null);\r\n const [page, setPage] = useState(1);\r\n const [perPage, setPerPage] = useState(pageSize);\r\n\r\n const totalPages = useMemo(\r\n () => Math.max(1, Math.ceil(data.length / perPage)),\r\n [data.length, perPage],\r\n );\r\n\r\n const safePage = Math.min(page, totalPages);\r\n\r\n const displayData = useMemo(\r\n () => data.slice((safePage - 1) * perPage, safePage * perPage),\r\n [data, safePage, perPage],\r\n );\r\n\r\n const paginationRange = useMemo(() => {\r\n const half = Math.floor(VISIBLE_PAGES / 2);\r\n let start = Math.max(1, safePage - half);\r\n let end = Math.min(totalPages, start + VISIBLE_PAGES - 1);\r\n if (end - start + 1 < VISIBLE_PAGES) {\r\n start = Math.max(1, end - VISIBLE_PAGES + 1);\r\n }\r\n const range: (number | \"...\")[] = [];\r\n if (start > 1) {\r\n range.push(1);\r\n if (start > 2) range.push(\"...\");\r\n }\r\n for (let i = start; i <= end; i++) range.push(i);\r\n if (end < totalPages) {\r\n if (end < totalPages - 1) range.push(\"...\");\r\n range.push(totalPages);\r\n }\r\n return range;\r\n }, [safePage, totalPages]);\r\n\r\n const handlePageSizeChange = useCallback((value: number) => {\r\n setPerPage(value);\r\n setPage(1);\r\n }, []);\r\n\r\n const colCount = columns.length;\r\n const colWidth = colCount > 0 ? `${Math.round(100 / colCount)}%` : \"auto\";\r\n\r\n const handleMouseEnter = (\r\n e: React.MouseEvent<HTMLDivElement>,\r\n content: string,\r\n ) => {\r\n const rect = e.currentTarget.getBoundingClientRect();\r\n setTooltip({\r\n content,\r\n x: rect.left + rect.width / 2,\r\n y: rect.top,\r\n });\r\n };\r\n\r\n const handleMouseLeave = () => {\r\n setTooltip(null);\r\n };\r\n\r\n const banner = error ? (\r\n <div className=\"mb-4\">\r\n <ErrorDisplay key={error.message} error={error} />\r\n </div>\r\n ) : null;\r\n\r\n if (loading) {\r\n return (\r\n <div className=\"w-full overflow-x-auto\">\r\n {banner}\r\n <div className=\"rounded-lg shadow-md border border-gray-200\">\r\n <div className=\"flex items-center justify-center py-20 text-gray-500\">\r\n Chargement...\r\n </div>\r\n </div>\r\n </div>\r\n );\r\n }\r\n\r\n if (!data || data.length === 0) {\r\n return (\r\n <div className=\"w-full overflow-x-auto\">\r\n {banner}\r\n <div className=\"rounded-lg shadow-md border border-gray-200\">\r\n <div className=\"flex items-center justify-center py-20 text-gray-500\">\r\n Aucun élément\r\n </div>\r\n </div>\r\n </div>\r\n );\r\n }\r\n\r\n return (\r\n <div className=\"w-full overflow-x-auto\">\r\n {banner}\r\n <div className=\"flex items-center justify-between mb-2\">\r\n {label && (\r\n <div className=\"text-sm font-semibold text-gray-700\">\r\n {label}: {data.length}\r\n </div>\r\n )}\r\n {printable && (\r\n <button\r\n onClick={() => window.print()}\r\n className=\"flex items-center gap-2 px-4 py-2 text-sm font-medium text-white bg-blue-500 rounded-lg hover:bg-blue-600 transition-colors print:hidden\"\r\n >\r\n <Printer className=\"w-4 h-4\" />\r\n Imprimer\r\n </button>\r\n )}\r\n </div>\r\n <div className=\"rounded-lg shadow-md border border-gray-200\">\r\n <table className=\"w-full table-fixed divide-y divide-gray-200 print:table-fixed\">\r\n <thead className=\"bg-blue-500 rounded-t-lg\">\r\n <tr>\r\n {columns.map((col, index) => (\r\n <th\r\n key={index}\r\n style={{ width: colWidth }}\r\n className={clsx(\r\n \"px-6 py-3 text-left text-xs font-bold text-white uppercase tracking-wider truncate\",\r\n col.excludeFromPrint && \"print:hidden\",\r\n )}\r\n >\r\n {col.header}\r\n </th>\r\n ))}\r\n </tr>\r\n </thead>\r\n <tbody\r\n className={clsx(\r\n \"bg-white divide-y divide-gray-200\",\r\n printable && \"print:hidden\",\r\n )}\r\n >\r\n {displayData.map((row, rowIndex) => (\r\n <tr\r\n key={rowIndex}\r\n className=\"hover:bg-gray-100 transition-colors duration-200\"\r\n >\r\n {columns.map((col, colIndex) => {\r\n const cellContent = col.render\r\n ? col.render(row)\r\n : String(row[col.accessor!]);\r\n const textContent =\r\n typeof cellContent === \"string\" ? cellContent : \"\";\r\n\r\n return (\r\n <td\r\n key={colIndex}\r\n style={{ width: colWidth }}\r\n className={clsx(\r\n \"px-6 py-4 text-sm text-gray-700\",\r\n col.excludeFromPrint && \"print:hidden\",\r\n )}\r\n >\r\n {typeof cellContent === \"string\" ? (\r\n <div\r\n className=\"truncate\"\r\n onMouseEnter={(e) => handleMouseEnter(e, textContent)}\r\n onMouseLeave={handleMouseLeave}\r\n >\r\n {cellContent}\r\n </div>\r\n ) : (\r\n cellContent\r\n )}\r\n </td>\r\n );\r\n })}\r\n </tr>\r\n ))}\r\n </tbody>\r\n {printable && (\r\n <tbody className=\"hidden print:table-row-group\">\r\n {data.map((row, rowIndex) => (\r\n <tr key={rowIndex}>\r\n {columns.map((col, colIndex) => {\r\n const cellContent = col.render\r\n ? col.render(row)\r\n : String(row[col.accessor!]);\r\n\r\n return (\r\n <td\r\n key={colIndex}\r\n style={{ width: colWidth }}\r\n className={clsx(\r\n \"px-6 py-4 text-sm text-gray-700\",\r\n col.excludeFromPrint && \"print:hidden\",\r\n )}\r\n >\r\n {cellContent}\r\n </td>\r\n );\r\n })}\r\n </tr>\r\n ))}\r\n </tbody>\r\n )}\r\n </table>\r\n </div>\r\n\r\n {showPagination && totalPages > 1 && (\r\n <div className=\"flex items-center justify-between mt-4 text-sm print:hidden\">\r\n <div className=\"flex items-center gap-2 text-gray-600\">\r\n <span>Lignes par page :</span>\r\n <select\r\n value={perPage}\r\n onChange={(e) => handlePageSizeChange(Number(e.target.value))}\r\n className=\"border border-gray-300 rounded px-2 py-1 text-sm bg-white focus:outline-none focus:ring-2 focus:ring-blue-400\"\r\n >\r\n {pageSizeOptions.map((opt) => (\r\n <option key={opt} value={opt}>\r\n {opt}\r\n </option>\r\n ))}\r\n </select>\r\n </div>\r\n\r\n <div className=\"flex items-center gap-1\">\r\n <button\r\n onClick={() => setPage((p) => Math.max(1, p - 1))}\r\n disabled={safePage <= 1}\r\n className={clsx(\r\n \"p-1.5 rounded transition-colors\",\r\n safePage <= 1\r\n ? \"text-gray-300 cursor-not-allowed\"\r\n : \"text-gray-600 hover:bg-gray-100\",\r\n )}\r\n >\r\n <ChevronLeft className=\"w-4 h-4\" />\r\n </button>\r\n\r\n {paginationRange.map((item, i) =>\r\n item === \"...\" ? (\r\n <span key={`ellipsis-${i}`} className=\"px-2 text-gray-400\">\r\n ...\r\n </span>\r\n ) : (\r\n <button\r\n key={item}\r\n onClick={() => setPage(item)}\r\n className={clsx(\r\n \"min-w-8 px-2 py-1 rounded text-sm font-medium transition-colors\",\r\n item === safePage\r\n ? \"bg-blue-500 text-white\"\r\n : \"text-gray-600 hover:bg-gray-100\",\r\n )}\r\n >\r\n {item}\r\n </button>\r\n ),\r\n )}\r\n\r\n <button\r\n onClick={() => setPage((p) => Math.min(totalPages, p + 1))}\r\n disabled={safePage >= totalPages}\r\n className={clsx(\r\n \"p-1.5 rounded transition-colors\",\r\n safePage >= totalPages\r\n ? \"text-gray-300 cursor-not-allowed\"\r\n : \"text-gray-600 hover:bg-gray-100\",\r\n )}\r\n >\r\n <ChevronRight className=\"w-4 h-4\" />\r\n </button>\r\n </div>\r\n\r\n <div className=\"text-gray-500\">\r\n Page {safePage} sur {totalPages}\r\n </div>\r\n </div>\r\n )}\r\n\r\n {tooltip && (\r\n <div\r\n className=\"fixed z-20 px-3 py-2 text-sm text-white bg-gray-800 rounded-lg shadow-lg pointer-events-none whitespace-nowrap\"\r\n style={{\r\n left: tooltip.x,\r\n top: tooltip.y - 8,\r\n transform: \"translate(-50%, -100%)\",\r\n }}\r\n >\r\n {tooltip.content}\r\n </div>\r\n )}\r\n <style>{`\r\n @media print {\r\n body * { visibility: hidden; }\r\n .w-full.overflow-x-auto { visibility: visible; }\r\n .w-full.overflow-x-auto * { visibility: visible; }\r\n .w-full.overflow-x-auto { position: absolute; left: 0; top: 0; width: 100%; }\r\n }\r\n `}</style>\r\n </div>\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport { X } from \"lucide-react\";\r\nimport { ApiError } from \"../../../utils/src\";\r\nimport { useState } from \"react\";\r\n\r\ninterface ErrorDisplayProps {\r\n error: ApiError | null;\r\n}\r\n\r\nexport function ErrorDisplay({ error }: ErrorDisplayProps) {\r\n const [dismissed, setDismissed] = useState(false);\r\n\r\n if (!error || dismissed) return null;\r\n\r\n return (\r\n <div className=\"w-full overflow-x-auto\">\r\n <div className=\"rounded-lg shadow-md border border-red-200 bg-red-50\">\r\n <div className=\"flex items-start justify-between gap-4 px-4 py-4\">\r\n <div className=\"flex flex-col gap-1\">\r\n <p className=\"text-red-700 font-medium\">Erreur</p>\r\n <p className=\"text-red-600 text-sm\">{error.message}</p>\r\n </div>\r\n <button\r\n onClick={() => setDismissed(true)}\r\n className=\"text-red-400 hover:text-red-600 shrink-0 cursor-pointer\"\r\n >\r\n <X className=\"w-5 h-5\" />\r\n </button>\r\n </div>\r\n </div>\r\n </div>\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport React, { useState, useRef, useEffect } from \"react\";\r\nimport { Ellipsis } from \"lucide-react\";\r\n\r\nexport type TableAction<T> = {\r\n label: string;\r\n icon: React.ReactNode;\r\n callback: (row: T) => void;\r\n color?: string;\r\n};\r\n\r\ntype ActionsMenuProps<T> = {\r\n row: T;\r\n actions: TableAction<T>[];\r\n};\r\n\r\nexport function ActionsMenu<T>({ row, actions }: ActionsMenuProps<T>) {\r\n const [isOpen, setIsOpen] = useState(false);\r\n const [coords, setCoords] = useState({ top: 0, left: 0 });\r\n const buttonRef = useRef<HTMLButtonElement>(null);\r\n const menuRef = useRef<HTMLDivElement>(null);\r\n\r\n // Fermer le menu si clic en dehors\r\n useEffect(() => {\r\n function handleClickOutside(event: MouseEvent) {\r\n if (\r\n menuRef.current &&\r\n buttonRef.current &&\r\n !menuRef.current.contains(event.target as Node) &&\r\n !buttonRef.current.contains(event.target as Node)\r\n ) {\r\n setIsOpen(false);\r\n }\r\n }\r\n\r\n document.addEventListener(\"mousedown\", handleClickOutside);\r\n return () => document.removeEventListener(\"mousedown\", handleClickOutside);\r\n }, []);\r\n\r\n const toggleMenu = () => {\r\n if (buttonRef.current) {\r\n const rect = buttonRef.current.getBoundingClientRect();\r\n const menuWidth = 180;\r\n const menuHeight = actions.length * 40;\r\n\r\n const spaceBelow = window.innerHeight - rect.bottom;\r\n const spaceRight = window.innerWidth - rect.left;\r\n\r\n let top = rect.bottom;\r\n let left = rect.left;\r\n\r\n // If not enough space below, show above\r\n if (spaceBelow < menuHeight + 20) {\r\n top = rect.top - menuHeight;\r\n }\r\n\r\n // If not enough space on the right, align to the left\r\n if (spaceRight < menuWidth + 20) {\r\n left = rect.left - menuWidth + 30;\r\n }\r\n\r\n setCoords({ top, left });\r\n }\r\n setIsOpen(!isOpen);\r\n };\r\n\r\n return (\r\n <>\r\n <button\r\n ref={buttonRef}\r\n onClick={toggleMenu}\r\n className=\"p-1 hover:bg-gray-100 rounded-full\"\r\n >\r\n <Ellipsis className=\"w-5 h-5\" />\r\n </button>\r\n\r\n {isOpen && (\r\n <div\r\n ref={menuRef}\r\n className=\"fixed bg-white border border-gray-200 rounded shadow-lg z-20\"\r\n style={{\r\n top: coords.top,\r\n left: coords.left,\r\n minWidth: 180,\r\n }}\r\n >\r\n {actions.map((action, idx) => (\r\n <button\r\n key={idx}\r\n className={`flex items-center gap-2 px-4 py-2 w-full text-sm hover:bg-gray-100 ${\r\n action.color || \"text-gray-700\"\r\n }`}\r\n onClick={() => {\r\n action.callback(row);\r\n setIsOpen(false);\r\n }}\r\n >\r\n {action.icon}\r\n {action.label}\r\n </button>\r\n ))}\r\n </div>\r\n )}\r\n </>\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport { X } from \"lucide-react\";\r\nimport React, { useEffect } from \"react\";\r\nimport { createPortal } from \"react-dom\";\r\n\r\ntype ModalProps = {\r\n title: string;\r\n isOpen: boolean;\r\n onClose: () => void;\r\n children: React.ReactNode | ((requestClose: () => void) => React.ReactNode);\r\n};\r\n\r\nexport function Modal({ title, isOpen, onClose, children }: ModalProps) {\r\n const requestClose = () => {\r\n onClose();\r\n };\r\n\r\n useEffect(() => {\r\n if (isOpen) {\r\n document.body.style.overflow = \"hidden\";\r\n }\r\n\r\n return () => {\r\n document.body.style.overflow = \"\";\r\n };\r\n }, [isOpen]);\r\n\r\n useEffect(() => {\r\n function handleEsc(e: KeyboardEvent) {\r\n if (e.key === \"Escape\") {\r\n onClose();\r\n }\r\n }\r\n\r\n if (isOpen) {\r\n document.addEventListener(\"keydown\", handleEsc);\r\n }\r\n\r\n return () => {\r\n document.removeEventListener(\"keydown\", handleEsc);\r\n };\r\n }, [isOpen, onClose]);\r\n\r\n if (!isOpen) return null;\r\n\r\n const content =\r\n typeof children === \"function\" ? children(requestClose) : children;\r\n\r\n return createPortal(\r\n <div className=\"fixed inset-0 z-50 flex items-center justify-center\">\r\n <div\r\n className=\"absolute inset-0 bg-black/20 backdrop-blur-sm\"\r\n onClick={onClose}\r\n />\r\n\r\n <div className=\"relative bg-white rounded-lg shadow-lg w-full max-w-2xl mx-4 p-6 flex flex-col max-h-[85vh]\">\r\n <div className=\"flex items-center justify-between mb-4 border-b-2 border-gray-400 pb-3 sticky top-0 bg-white z-10\">\r\n <h2 className=\"text-lg font-semibold text-gray-900\">{title}</h2>\r\n\r\n <button\r\n onClick={onClose}\r\n className=\"text-gray-500 hover:text-gray-700 text-xl cursor-pointer\"\r\n >\r\n <X />\r\n </button>\r\n </div>\r\n\r\n <div className=\"overflow-y-auto flex-1 min-h-0\">{content}</div>\r\n </div>\r\n </div>,\r\n document.body,\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport { useCallback, useEffect, useRef, useState } from \"react\";\r\nimport { ApiError } from \"../../../utils/src/fetcher\";\r\nimport { CircleQuestionMark } from \"lucide-react\";\r\n\r\nconst ERROR_COUNTDOWN = 10;\r\n\r\ninterface ConfirmationProps {\r\n question: string;\r\n messageYes: string;\r\n messageNo: string;\r\n requestClose: () => void;\r\n onAction: () =>\r\n | void\r\n | Promise<void>\r\n | Promise<boolean>\r\n | Promise<{ success: true }>;\r\n isProcessing: boolean;\r\n error: ApiError | null;\r\n resetRequest: () => void;\r\n}\r\n\r\nexport function Confirmation({\r\n question,\r\n messageYes,\r\n messageNo,\r\n requestClose,\r\n onAction,\r\n isProcessing,\r\n error,\r\n resetRequest,\r\n}: ConfirmationProps) {\r\n const [countdown, setCountdown] = useState(0);\r\n const countdownRef = useRef<number | null>(null);\r\n const resetRequestRef = useRef(resetRequest);\r\n\r\n useEffect(() => {\r\n resetRequestRef.current = resetRequest;\r\n }, [resetRequest]);\r\n\r\n const clearCountdown = useCallback(() => {\r\n if (countdownRef.current !== null) {\r\n window.clearInterval(countdownRef.current);\r\n countdownRef.current = null;\r\n }\r\n }, []);\r\n\r\n const resetConfirmationState = useCallback(() => {\r\n clearCountdown();\r\n setCountdown(0);\r\n }, [clearCountdown]);\r\n\r\n const handleResetRequest = useCallback(() => {\r\n resetConfirmationState();\r\n resetRequest();\r\n }, [resetConfirmationState, resetRequest]);\r\n\r\n const handleRequestClose = useCallback(() => {\r\n resetConfirmationState();\r\n resetRequest();\r\n requestClose();\r\n }, [requestClose, resetConfirmationState, resetRequest]);\r\n\r\n const handleAction = useCallback(async () => {\r\n try {\r\n await onAction();\r\n handleRequestClose();\r\n } catch {\r\n // L'erreur est propagée par le parent via la prop `error`.\r\n }\r\n }, [handleRequestClose, onAction]);\r\n\r\n useEffect(() => {\r\n clearCountdown();\r\n\r\n if (!error) {\r\n const resetTimeoutId = window.setTimeout(() => {\r\n setCountdown(0);\r\n }, 0);\r\n\r\n return () => {\r\n window.clearTimeout(resetTimeoutId);\r\n };\r\n }\r\n\r\n const startCountdownTimeoutId = window.setTimeout(() => {\r\n setCountdown(ERROR_COUNTDOWN);\r\n\r\n countdownRef.current = window.setInterval(() => {\r\n setCountdown((previousCountdown) => {\r\n if (previousCountdown <= 1) {\r\n clearCountdown();\r\n window.setTimeout(() => {\r\n resetRequestRef.current();\r\n }, 0);\r\n\r\n return 0;\r\n }\r\n\r\n return previousCountdown - 1;\r\n });\r\n }, 1000);\r\n }, 0);\r\n\r\n return () => {\r\n window.clearTimeout(startCountdownTimeoutId);\r\n clearCountdown();\r\n };\r\n }, [clearCountdown, error]);\r\n\r\n useEffect(() => {\r\n return () => {\r\n clearCountdown();\r\n resetRequestRef.current();\r\n };\r\n }, [clearCountdown]);\r\n\r\n const isErrorVisible = Boolean(error) && countdown > 0;\r\n\r\n if (!question) return null;\r\n\r\n return (\r\n <div className=\"flex flex-col items-center gap-3 z-40\">\r\n <CircleQuestionMark className=\"text-red-500 text-5xl\" />\r\n <h2 className=\"text-xl font-bold text-red-500\">Confirmation requise</h2>\r\n\r\n <p className=\"mt-4 text-md leading-relaxed text-gray-700\">{question}</p>\r\n\r\n <div className=\"mt-6 flex w-full gap-3\">\r\n <button\r\n type=\"button\"\r\n onClick={handleRequestClose}\r\n disabled={isProcessing}\r\n className=\"w-full rounded-lg border border-gray-300 bg-white px-4 py-2 text-sm font-semibold text-gray-700 transition hover:cursor-pointer hover:bg-gray-100 disabled:cursor-not-allowed disabled:opacity-50 disabled:hover:bg-white\"\r\n >\r\n {messageNo}\r\n </button>\r\n\r\n <button\r\n type=\"button\"\r\n onClick={handleAction}\r\n disabled={isProcessing}\r\n className=\"w-full rounded-lg bg-red-400 px-4 py-2 text-sm font-semibold text-white transition hover:cursor-pointer hover:bg-red-500 active:scale-95 disabled:opacity-50 disabled:hover:bg-red-500\"\r\n >\r\n {isProcessing ? \"operation en cours\" : messageYes}\r\n </button>\r\n </div>\r\n\r\n {error && isErrorVisible && (\r\n <div className=\"mt-4 w-full rounded-lg border border-red-200 bg-red-50 p-4 text-left text-sm text-red-700\">\r\n <div className=\"flex items-start justify-between gap-3\">\r\n <div>\r\n <p className=\"font-semibold\">Erreur</p>\r\n <p className=\"mt-1 text-sm\">{error.message}</p>\r\n </div>\r\n\r\n <button\r\n type=\"button\"\r\n onClick={handleResetRequest}\r\n className=\"rounded-full bg-red-100 px-2 py-1 text-xs font-semibold text-red-700 hover:bg-red-200\"\r\n >\r\n Fermer\r\n </button>\r\n </div>\r\n\r\n <p className=\"mt-3 text-xs text-red-600\">\r\n Ce message disparait dans {countdown}s...\r\n </p>\r\n </div>\r\n )}\r\n </div>\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport React from \"react\";\r\n\r\ntype HeaderContentProps = {\r\n title: string;\r\n description: string;\r\n\r\n actionLabel?: string;\r\n onAction?: () => void;\r\n icon?: React.ReactNode;\r\n};\r\n\r\nexport function HeaderContent({\r\n title,\r\n description,\r\n actionLabel,\r\n onAction,\r\n icon,\r\n}: HeaderContentProps) {\r\n return (\r\n <div className=\"flex flex-col md:flex-row md:items-center md:justify-between gap-4 mb-6\">\r\n <div>\r\n <h1 className=\"text-xl font-semibold text-gray-900 flex items-center gap-2\">\r\n {title}\r\n </h1>\r\n\r\n {description && (\r\n <p className=\"text-sm text-gray-500 mt-1\">{description}</p>\r\n )}\r\n </div>\r\n\r\n {actionLabel && onAction && (\r\n <button\r\n onClick={onAction}\r\n className=\"font-semibold md:inline-flex items-center gap-2 bg-gray-900 text-white px-4 py-2 rounded-md text-sm hover:bg-gray-700 transition hover:cursor-pointer\"\r\n >\r\n {icon && <span className=\"w-4 h-4\">{icon}</span>}\r\n {actionLabel}\r\n </button>\r\n )}\r\n </div>\r\n );\r\n}\r\n\r\n","import React, { useState, useEffect, useRef, useCallback } from \"react\";\r\nimport { ApiError } from \"../../../utils/src/fetcher\";\r\nimport { X } from \"lucide-react\";\r\n\r\ninterface FormProps extends React.FormHTMLAttributes<HTMLFormElement> {\r\n erreurs?: ApiError | null;\r\n onErrorClose?: () => void;\r\n}\r\n\r\nconst Form: React.FC<FormProps> = ({\r\n erreurs,\r\n onErrorClose,\r\n children,\r\n className,\r\n ...props\r\n}) => {\r\n const formClassName = [\"flex flex-col gap-3\", className]\r\n .filter(Boolean)\r\n .join(\" \");\r\n const errorMessage = erreurs?.message || null;\r\n const [showError, setShowError] = useState(!!erreurs);\r\n const [countdown, setCountdown] = useState(erreurs ? 10 : 0);\r\n const [animating, setAnimating] = useState(!!erreurs);\r\n const intervalRef = useRef<number | null>(null);\r\n const hasClosedRef = useRef(false);\r\n\r\n const closeError = useCallback(\r\n (triggerCallback = true) => {\r\n if (intervalRef.current !== null) {\r\n window.clearInterval(intervalRef.current);\r\n intervalRef.current = null;\r\n }\r\n\r\n setShowError(false);\r\n setAnimating(false);\r\n setCountdown(0);\r\n\r\n if (triggerCallback && onErrorClose && !hasClosedRef.current) {\r\n hasClosedRef.current = true;\r\n onErrorClose();\r\n }\r\n },\r\n [onErrorClose],\r\n );\r\n\r\n useEffect(() => {\r\n hasClosedRef.current = false;\r\n\r\n if (!erreurs) {\r\n const closeTimeout = window.setTimeout(() => closeError(false), 0);\r\n return () => {\r\n window.clearTimeout(closeTimeout);\r\n };\r\n }\r\n\r\n const initTimeout = window.setTimeout(() => {\r\n setShowError(true);\r\n setAnimating(true);\r\n setCountdown(10);\r\n }, 0);\r\n\r\n intervalRef.current = window.setInterval(() => {\r\n setCountdown((prev) => {\r\n if (prev <= 1) {\r\n closeError(true);\r\n return 0;\r\n }\r\n return prev - 1;\r\n });\r\n }, 1000);\r\n\r\n return () => {\r\n window.clearTimeout(initTimeout);\r\n if (intervalRef.current !== null) {\r\n window.clearInterval(intervalRef.current);\r\n intervalRef.current = null;\r\n }\r\n };\r\n }, [erreurs, closeError]);\r\n\r\n return (\r\n <>\r\n <form className={formClassName} {...props}>\r\n {children}\r\n </form>\r\n {showError && errorMessage && (\r\n <div\r\n className={`fixed top-0 left-0 right-0 z-[9999] bg-red-500 text-white p-4 rounded-b-md shadow-lg flex justify-between items-center transition-transform duration-300 ${\r\n animating\r\n ? \"transform translate-y-0\"\r\n : \"transform -translate-y-full\"\r\n }`}\r\n >\r\n <span>{errorMessage}</span>\r\n <div className=\"flex items-center\">\r\n <span className=\"mr-2\">{countdown}s</span>\r\n <button onClick={() => closeError(true)}>\r\n <X size={20} />\r\n </button>\r\n </div>\r\n </div>\r\n )}\r\n </>\r\n );\r\n};\r\n\r\nexport { Form };\r\n","import React from \"react\";\r\n\r\ninterface FieldContainerProps {\r\n children: React.ReactNode;\r\n className?: string;\r\n}\r\n\r\nexport function FieldContainer({ children, className }: FieldContainerProps) {\r\n return (\r\n <div className={`flex flex-col gap-2 mb-3 relative ${className ?? \"\"}`}>\r\n <div className=\"flex flex-col gap-1\">{children}</div>\r\n </div>\r\n );\r\n}\r\n","import React from \"react\";\r\n\r\ninterface LabelProps extends Omit<\r\n React.LabelHTMLAttributes<HTMLLabelElement>,\r\n \"required\"\r\n> {\r\n required?: boolean;\r\n}\r\n\r\nconst Label = React.forwardRef<HTMLLabelElement, LabelProps>(\r\n ({ required, children, className, ...props }, ref) => {\r\n return (\r\n <label\r\n ref={ref}\r\n className={`font-semibold text-gray-600 block ${className ?? \"\"}`.trim()}\r\n {...props}\r\n >\r\n {children}\r\n {required ? <span className=\"text-red-500 ml-1\">*</span> : null}\r\n </label>\r\n );\r\n },\r\n);\r\n\r\nLabel.displayName = \"Label\";\r\n\r\nexport { Label };\r\n","import React, { useState } from \"react\";\r\nimport { Eye, EyeOff } from \"lucide-react\";\r\n\r\nconst Input = React.forwardRef<\r\n HTMLInputElement,\r\n React.InputHTMLAttributes<HTMLInputElement>\r\n>(({ type, className, ...props }, ref) => {\r\n const [showPassword, setShowPassword] = useState(false);\r\n\r\n const isPassword = type === \"password\";\r\n const inputType = isPassword ? (showPassword ? \"text\" : \"password\") : type;\r\n\r\n return (\r\n <div className=\"relative\">\r\n <input\r\n ref={ref}\r\n type={inputType}\r\n className={`w-full px-3 py-2 pr-10 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-gray-500 focus:border-transparent transition duration-200 ${className || \"\"}`}\r\n {...props}\r\n />\r\n {isPassword && (\r\n <button\r\n type=\"button\"\r\n onClick={() => setShowPassword(!showPassword)}\r\n className=\"absolute inset-y-0 right-0 pr-3 flex items-center text-gray-500 hover:text-gray-700\"\r\n >\r\n {showPassword ? <EyeOff size={20} /> : <Eye size={20} />}\r\n </button>\r\n )}\r\n </div>\r\n );\r\n});\r\n\r\nInput.displayName = \"Input\";\r\n\r\nexport { Input };\r\n","import React from \"react\";\r\n\r\nconst Select = React.forwardRef<\r\n HTMLSelectElement,\r\n React.SelectHTMLAttributes<HTMLSelectElement>\r\n>(({ className, ...props }, ref) => {\r\n return (\r\n <select\r\n ref={ref}\r\n className={`w-full px-3 py-2 pr-10 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-gray-500 focus:border-transparent transition duration-200 bg-white cursor-pointer appearance-none bg-no-repeat bg-right bg-contain ${className || \"\"}`}\r\n style={{\r\n backgroundImage: `url(\"data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' fill='none' viewBox='0 0 20 20'%3e%3cpath stroke='%236b7280' stroke-linecap='round' stroke-linejoin='round' stroke-width='1.5' d='m6 8 4 4 4-4'/%3e%3c/svg%3e\")`,\r\n backgroundPosition: \"right 0.75rem center\",\r\n backgroundSize: \"1.25em 1.25em\",\r\n }}\r\n {...props}\r\n />\r\n );\r\n});\r\n\r\nSelect.displayName = \"Select\";\r\n\r\nexport { Select };\r\n\r\n// Option Component\r\n\r\nconst Option = React.forwardRef<\r\n HTMLOptionElement,\r\n React.OptionHTMLAttributes<HTMLOptionElement>\r\n>(({ ...props }, ref) => {\r\n return <option ref={ref} {...props} />;\r\n});\r\n\r\nOption.displayName = \"Option\";\r\n\r\nexport { Option };\r\n","import React from \"react\";\r\n\r\nconst TextArea = React.forwardRef<\r\n HTMLTextAreaElement,\r\n React.TextareaHTMLAttributes<HTMLTextAreaElement>\r\n>(({ ...props }, ref) => {\r\n return (\r\n <textarea\r\n ref={ref}\r\n className=\"w-full px-3 py-2 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-gray-500 focus:border-transparent transition duration-200 resize-none\"\r\n {...props}\r\n />\r\n );\r\n});\r\n\r\nTextArea.displayName = \"TextArea\";\r\n\r\nexport { TextArea };\r\n","import React from \"react\";\r\n\r\nconst DatePicker = React.forwardRef<\r\n HTMLInputElement,\r\n React.InputHTMLAttributes<HTMLInputElement>\r\n>(({ className, placeholder, required, ...props }, ref) => {\r\n return (\r\n <div className=\"relative\">\r\n <input\r\n ref={ref}\r\n type=\"date\"\r\n required={required ?? true}\r\n className={`peer w-full px-3 py-2 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-gray-500 focus:border-transparent transition duration-200 ${className ?? \"\"}`}\r\n {...props}\r\n />\r\n <span className=\"absolute left-3 top-1/2 -translate-y-1/2 text-gray-400 pointer-events-none peer-valid:hidden md:hidden\">\r\n {placeholder ?? \"jj/mm/aaaa\"}\r\n </span>\r\n </div>\r\n );\r\n});\r\n\r\nDatePicker.displayName = \"DatePicker\";\r\n\r\nexport { DatePicker };\r\n","import { Loader } from \"lucide-react\";\r\n\r\ninterface LoadingProps {\r\n text: string;\r\n}\r\n\r\nexport function Loading(props: LoadingProps) {\r\n return (\r\n <div className=\"flex items-center justify-center\">\r\n <div className=\"flex flex-col items-center gap-4\">\r\n <Loader className=\"animate-spin\" size={40} />\r\n\r\n <p className=\"text-gray-600 text-md font-medium\">{props.text}</p>\r\n </div>\r\n </div>\r\n );\r\n}\r\n","\"use client\";\r\n\r\nimport { LoaderCircle } from \"lucide-react\";\r\n\r\ninterface LoaderSubmitProps {\r\n label: string;\r\n loadingLabel: string;\r\n isLoading: boolean;\r\n}\r\n\r\nexport function LoaderSubmit({ label, loadingLabel, isLoading }: LoaderSubmitProps) {\r\n return (\r\n <>\r\n {isLoading ? (\r\n <div className=\"flex flex-row gap-2 items-center\">\r\n <LoaderCircle className=\"animate-spin text-gray-500\" />\r\n <p className=\"text-gray-500 font-semibold\">{loadingLabel}</p>\r\n </div>\r\n ) : (\r\n <button\r\n type=\"submit\"\r\n className=\"bg-gray-900 text-white px-6 py-2 rounded-md hover:bg-gray-700 hover:cursor-pointer transition-colors duration-300 font-semibold shadow-md\"\r\n disabled={isLoading}\r\n >\r\n {label}\r\n </button>\r\n )}\r\n </>\r\n );\r\n}\r\n","\"use client\";\n\nimport { useRouter } from \"next/navigation\";\nimport { useEffect, useState } from \"react\";\n\ninterface SessionExpiredProps {\n redirectUrl?: string;\n}\n\nexport function SessionExpired({ redirectUrl = \"/\" }: SessionExpiredProps) {\n const router = useRouter();\n const [countdown, setCountdown] = useState(10);\n\n useEffect(() => {\n if (countdown <= 0) {\n router.push(redirectUrl);\n return;\n }\n const timer = setTimeout(() => setCountdown((c) => c - 1), 1000);\n return () => clearTimeout(timer);\n }, [countdown, router, redirectUrl]);\n\n const handleConnect = () => {\n router.push(redirectUrl);\n };\n\n return (\n <div className=\"min-h-screen flex items-center justify-center bg-gray-50\">\n <div className=\"max-w-md w-full text-center space-y-8 p-8\">\n <div className=\"space-y-3\">\n <div className=\"flex justify-center\">\n <svg\n className=\"w-16 h-16 text-gray-300\"\n fill=\"none\"\n viewBox=\"0 0 24 24\"\n stroke=\"currentColor\"\n strokeWidth={1.5}\n >\n <path\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n d=\"M16.5 10.5V6.75a4.5 4.5 0 10-9 0v3.75m-.75 11.25h10.5a2.25 2.25 0 002.25-2.25v-6.75a2.25 2.25 0 00-2.25-2.25H6.75a2.25 2.25 0 00-2.25 2.25v6.75a2.25 2.25 0 002.25 2.25z\"\n />\n </svg>\n </div>\n <h1 className=\"text-2xl font-semibold text-gray-900\">\n Session expirée\n </h1>\n <p className=\"text-gray-500\">\n Votre session a expiré ou vous n&apos;êtes pas connecté.\n Veuillez vous reconnecter pour accéder à cette page.\n </p>\n </div>\n\n <button\n onClick={handleConnect}\n className=\"bg-gray-900 text-white px-6 py-2.5 rounded-md text-sm font-semibold hover:bg-gray-700 transition-colors\"\n >\n Me connecter\n </button>\n\n <p className=\"text-sm text-gray-400\">\n Redirection automatique dans {countdown}s...\n </p>\n </div>\n </div>\n );\n}\n","\"use client\";\n\nimport Image from \"next/image\";\nimport Link from \"next/link\";\n\ninterface AccessDeniedProps {\n logo: string;\n redirectTo: string;\n textRedirection: string;\n}\n\nexport function AccessDenied({ logo, redirectTo, textRedirection }: AccessDeniedProps) {\n return (\n <main className=\"min-h-screen py-16 px-4 bg-gradient-to-b from-gray-100 to-white text-gray-900 flex items-center justify-center\">\n <div className=\"max-w-md mx-auto text-center\">\n <div className=\"flex justify-center mb-6\">\n <Image\n alt=\"Logo\"\n height={100}\n width={100}\n src={logo}\n />\n </div>\n\n <h1 className=\"text-2xl font-bold text-red-600 mb-4\">\n Accès refusé\n </h1>\n\n <p className=\"text-gray-500 mb-8\">\n Vous ne disposez pas des droits nécessaires pour accéder à cette page.\n </p>\n\n <Link\n href={redirectTo}\n className=\"inline-block px-6 py-3 bg-gray-900 text-white rounded-lg font-semibold hover:bg-gray-700 transition-colors\"\n >\n {textRedirection}\n </Link>\n </div>\n </main>\n );\n}\n","\"use client\";\n\nimport {\n createContext,\n useContext,\n useMemo,\n type ComponentType,\n type ReactNode,\n} from \"react\";\nimport { redirect, usePathname } from \"next/navigation\";\n\nexport type UseCurrentUser = () => {\n data?: { role: { name: string } } | null;\n isLoading: boolean;\n};\n\nexport interface RouteGuardInputConfig {\n useCurrentUser: UseCurrentUser;\n pagePermissions: Record<string, string[]>;\n deniedPath?: string;\n}\n\nexport interface RouteGuardConfig {\n useCurrentUser: UseCurrentUser;\n pagePermissions: Record<string, string[]>;\n deniedPath: string;\n}\n\nexport function createRouteGuardConfig(\n input: RouteGuardInputConfig\n): RouteGuardConfig {\n return {\n useCurrentUser: input.useCurrentUser,\n pagePermissions: input.pagePermissions,\n deniedPath: input.deniedPath ?? \"/access-denied\",\n };\n}\n\nconst RouteGuardContext = createContext<RouteGuardConfig | null>(null);\n\ninterface RouteGuardProviderProps {\n children: ReactNode;\n config?: RouteGuardConfig;\n useCurrentUser?: UseCurrentUser;\n pagePermissions?: Record<string, string[]>;\n deniedPath?: string;\n}\n\nexport function RouteGuardProvider({\n children,\n config,\n useCurrentUser,\n pagePermissions,\n deniedPath,\n}: RouteGuardProviderProps) {\n const resolved = useMemo<RouteGuardConfig>(() => {\n if (config) return config;\n return {\n useCurrentUser: useCurrentUser!,\n pagePermissions: pagePermissions!,\n deniedPath: deniedPath ?? \"/access-denied\",\n };\n }, [config, useCurrentUser, pagePermissions, deniedPath]);\n\n if (!resolved.useCurrentUser || !resolved.pagePermissions) {\n throw new Error(\n \"RouteGuardProvider requires either a `config` prop (from createRouteGuardConfig) \" +\n \"or `useCurrentUser` + `pagePermissions` directly.\"\n );\n }\n\n return (\n <RouteGuardContext.Provider value={resolved}>\n <AutoRouteGuard config={resolved}>{children}</AutoRouteGuard>\n </RouteGuardContext.Provider>\n );\n}\n\nfunction AutoRouteGuard({\n config,\n children,\n}: {\n config: RouteGuardConfig;\n children: ReactNode;\n}) {\n const pathname = usePathname();\n const { data: user, isLoading } = config.useCurrentUser();\n\n const allowedRoles = useMemo(\n () => findAllowedRoles(pathname, config.pagePermissions),\n [pathname, config.pagePermissions]\n );\n\n if (!allowedRoles) {\n return <>{children}</>;\n }\n\n if (isLoading) {\n return (\n <div className=\"flex items-center justify-center min-h-screen\">\n <p className=\"text-gray-500\">Chargement...</p>\n </div>\n );\n }\n\n if (!user || !allowedRoles.includes(user.role.name)) {\n redirect(config.deniedPath);\n }\n\n return <>{children}</>;\n}\n\nexport function routeGuard(page: string, Component: ComponentType) {\n return function GuardedPage(props: Record<string, unknown>) {\n const config = useContext(RouteGuardContext);\n\n if (!config) {\n throw new Error(\n \"routeGuard requires a RouteGuardProvider ancestor. \" +\n \"Wrap your layout with <RouteGuardProvider>.\"\n );\n }\n\n const { data: user, isLoading } = config.useCurrentUser();\n const allowedRoles = findAllowedRoles(page, config.pagePermissions);\n\n if (!allowedRoles) {\n return <Component {...props} />;\n }\n\n if (isLoading) {\n return (\n <div className=\"flex items-center justify-center min-h-screen\">\n <p className=\"text-gray-500\">Chargement...</p>\n </div>\n );\n }\n\n if (!user || !allowedRoles.includes(user.role.name)) {\n redirect(config.deniedPath);\n }\n\n return <Component {...props} />;\n };\n}\n\nfunction findAllowedRoles(\n page: string,\n pagePermissions: Record<string, string[]>\n): string[] | undefined {\n const segments = page.split(\"/\").filter(Boolean);\n\n for (let i = 0; i <= segments.length; i++) {\n const candidate = \"/\" + segments.slice(0, i).join(\"/\");\n const roles = pagePermissions[candidate];\n if (roles) return roles;\n }\n\n return undefined;\n}\n","export class ApiError extends Error {\r\n public status: number;\r\n public code?: string;\r\n public data?: unknown;\r\n\r\n constructor(params: {\r\n message: string;\r\n status: number;\r\n code?: string;\r\n data?: unknown;\r\n }) {\r\n super(params.message);\r\n this.status = params.status;\r\n this.code = params.code;\r\n this.data = params.data;\r\n }\r\n}\r\n\r\ntype BackendErrorShape = {\r\n code?: string;\r\n status?: number;\r\n message?: string;\r\n};\r\n\r\nexport type FetcherOptions = RequestInit & {\r\n skipJsonParsing?: boolean;\r\n};\r\n\r\nexport async function fetcher<T = unknown>(\r\n url: string,\r\n options: FetcherOptions = {},\r\n): Promise<T> {\r\n const { headers, skipJsonParsing = false, ...rest } = options;\r\n\r\n const response = await fetch(url, {\r\n credentials: \"include\",\r\n headers: {\r\n \"Content-Type\": \"application/json\",\r\n ...headers,\r\n },\r\n ...rest,\r\n });\r\n\r\n let responseData: unknown = null;\r\n const contentType = response.headers.get(\"content-type\");\r\n\r\n if (!skipJsonParsing && contentType?.includes(\"application/json\")) {\r\n responseData = await response.json();\r\n }\r\n\r\n if (!response.ok) {\r\n const backendError = responseData as BackendErrorShape;\r\n\r\n throw new ApiError({\r\n message: backendError?.message || \"Une erreur est survenue\",\r\n status: backendError?.status || response.status,\r\n code: backendError?.code,\r\n data: responseData,\r\n });\r\n }\r\n\r\n return responseData as T;\r\n}\r\n","export class HttpError extends Error {\r\n status: number;\r\n code?: string;\r\n\r\n constructor(message: string, status = 400, code?: string) {\r\n super(message);\r\n\r\n this.name = \"HttpError\";\r\n this.status = status;\r\n this.code = code;\r\n\r\n Object.setPrototypeOf(this, HttpError.prototype);\r\n }\r\n}\r\n","import { HttpError } from \"./http-error\";\r\n\r\nconst GENERIC_MESSAGE = \"Erreur serveur\";\r\n\r\nfunction shouldShowDetails(showDetails?: boolean): boolean {\r\n return showDetails ?? process.env.NODE_ENV !== \"production\";\r\n}\r\n\r\nfunction sanitizedResponse(\r\n message: string,\r\n code: string,\r\n status: number,\r\n showDetails?: boolean,\r\n) {\r\n return Response.json(\r\n {\r\n message: showDetails ? message : GENERIC_MESSAGE,\r\n code: showDetails ? code : \"INTERNAL_ERROR\",\r\n status,\r\n },\r\n { status },\r\n );\r\n}\r\n\r\n/**\r\n * Transforme n'importe quelle erreur en réponse JSON standardisée\r\n * @param error L'erreur levée\r\n * @param defaultStatus Statut HTTP par défaut si non défini\r\n * @param showDetails Force l'affichage des détails (true) ou le mode sécurisé (false). Par défaut : automatique selon NODE_ENV\r\n * @returns Response JSON\r\n */\r\nexport function handleServerError(\r\n error: unknown,\r\n defaultStatus = 500,\r\n showDetails?: boolean,\r\n) {\r\n const details = shouldShowDetails(showDetails);\r\n\r\n console.error(\"Erreur capturée :\", error);\r\n\r\n // Cas HttpError personnalisé — toujours visible (erreur intentionnelle)\r\n if (error instanceof HttpError) {\r\n const status = error.status ?? defaultStatus;\r\n return Response.json(\r\n {\r\n message: error.message,\r\n code: error.code ?? \"INTERNAL_ERROR\",\r\n status,\r\n },\r\n { status },\r\n );\r\n }\r\n\r\n // Cas classique : objet Error\r\n if (error instanceof Error) {\r\n return sanitizedResponse(\r\n error.message,\r\n \"INTERNAL_ERROR\",\r\n defaultStatus,\r\n details,\r\n );\r\n }\r\n\r\n // Cas objet brut ou autre type\r\n if (typeof error === \"object\" && error !== null) {\r\n return sanitizedResponse(\r\n JSON.stringify(error),\r\n \"INTERNAL_ERROR\",\r\n defaultStatus,\r\n details,\r\n );\r\n }\r\n\r\n // Cas fallback : string ou autre\r\n return sanitizedResponse(\r\n String(error),\r\n \"INTERNAL_ERROR\",\r\n defaultStatus,\r\n details,\r\n );\r\n}\r\n","import { NextResponse } from \"next/server\";\r\nimport type { NextRequest } from \"next/server\";\r\nimport { jwtVerify } from \"jose\";\r\n\r\ninterface JwtPayload {\r\n id: string;\r\n role: string;\r\n permissions?: string[];\r\n}\r\n\r\ninterface AuthGuardOptions {\r\n publicRoutes: string[];\r\n loginUrl: string;\r\n jwtSecret: string;\r\n}\r\n\r\nexport async function authGuard(\r\n request: NextRequest,\r\n options: AuthGuardOptions,\r\n) {\r\n const { publicRoutes, loginUrl, jwtSecret } = options;\r\n\r\n if (!jwtSecret) {\r\n console.error(\"auth-guard: JWT_SECRET is not defined\");\r\n const loginUrlObj = new URL(loginUrl, request.url);\r\n loginUrlObj.searchParams.set(\"error\", \"authentification_requise\");\r\n return NextResponse.redirect(loginUrlObj);\r\n }\r\n\r\n const { pathname } = request.nextUrl;\r\n\r\n const isPublicRoute = publicRoutes.some((route) => {\r\n if (route.endsWith(\"/*\")) {\r\n return pathname.startsWith(route.slice(0, -2));\r\n }\r\n return pathname === route;\r\n });\r\n\r\n if (isPublicRoute) {\r\n return NextResponse.next();\r\n }\r\n\r\n const token = request.cookies.get(\"auth\")?.value;\r\n\r\n if (!token) {\r\n const loginUrlObj = new URL(loginUrl, request.url);\r\n loginUrlObj.searchParams.set(\"error\", \"authentification_requise\");\r\n return NextResponse.redirect(loginUrlObj);\r\n }\r\n\r\n let payload: JwtPayload;\r\n try {\r\n const secret = new TextEncoder().encode(jwtSecret);\r\n const result = await jwtVerify(token, secret, {\r\n algorithms: [\"HS256\"],\r\n });\r\n const rawPermissions = result.payload.permissions;\r\n payload = {\r\n id: String(result.payload.id || \"\"),\r\n role: String(result.payload.role || \"\"),\r\n permissions: Array.isArray(rawPermissions)\r\n ? (rawPermissions as string[])\r\n : [],\r\n };\r\n\r\n if (!payload.id || !payload.role) {\r\n const loginUrlObj = new URL(loginUrl, request.url);\r\n loginUrlObj.searchParams.set(\"error\", \"token_invalide\");\r\n return NextResponse.redirect(loginUrlObj);\r\n }\r\n } catch {\r\n const loginUrlObj = new URL(loginUrl, request.url);\r\n loginUrlObj.searchParams.set(\"error\", \"token_invalide\");\r\n return NextResponse.redirect(loginUrlObj);\r\n }\r\n\r\n const requestHeaders = new Headers(request.headers);\r\n requestHeaders.set(\"x-user-id\", payload.id);\r\n requestHeaders.set(\"x-user-role\", payload.role);\r\n requestHeaders.set(\r\n \"x-user-permissions\",\r\n (payload.permissions ?? []).join(\",\"),\r\n );\r\n\r\n return NextResponse.next({\r\n request: { headers: requestHeaders },\r\n });\r\n}\r\n"],"mappings":"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","names":["jsx","useState","useState","jsx","jsxs","jsx","jsxs","useState","useState","useEffect","jsx","jsxs","X","useEffect","jsx","jsxs","useCallback","useEffect","useRef","useState","jsx","jsxs","jsx","jsxs","useState","useEffect","useRef","useCallback","X","Fragment","jsx","jsxs","jsx","React","jsx","jsxs","React","useState","jsx","jsxs","React","jsx","React","jsx","React","jsx","React","jsx","jsxs","jsx","jsxs","Fragment","jsx","jsxs","useEffect","useState","jsx","jsxs","jsx","jsxs","useMemo","Fragment","jsx"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ramses1er/cbk-toolkit",
3
- "version": "1.12.0",
3
+ "version": "1.13.0",
4
4
  "type": "module",
5
5
  "main": "./dist/index.js",
6
6
  "module": "./dist/index.js",