@appcorp/fusion-storybook 0.1.4
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/README.md +147 -0
- package/base-modules/admission/cache.d.ts +14 -0
- package/base-modules/admission/cache.js +31 -0
- package/base-modules/admission/constants.d.ts +32 -0
- package/base-modules/admission/constants.js +37 -0
- package/base-modules/admission/context.d.ts +369 -0
- package/base-modules/admission/context.js +755 -0
- package/base-modules/admission/filter.d.ts +1 -0
- package/base-modules/admission/filter.js +31 -0
- package/base-modules/admission/form.d.ts +1 -0
- package/base-modules/admission/form.js +86 -0
- package/base-modules/admission/more-actions.d.ts +1 -0
- package/base-modules/admission/more-actions.js +5 -0
- package/base-modules/admission/page.d.ts +16 -0
- package/base-modules/admission/page.js +128 -0
- package/base-modules/admission/validate.d.ts +38 -0
- package/base-modules/admission/validate.js +70 -0
- package/base-modules/admission/view.d.ts +1 -0
- package/base-modules/admission/view.js +40 -0
- package/base-modules/discount-code/cache.d.ts +27 -0
- package/base-modules/discount-code/cache.js +46 -0
- package/base-modules/discount-code/constants.d.ts +19 -0
- package/base-modules/discount-code/constants.js +26 -0
- package/base-modules/discount-code/context.d.ts +154 -0
- package/base-modules/discount-code/context.js +416 -0
- package/base-modules/discount-code/filter.d.ts +9 -0
- package/base-modules/discount-code/filter.js +14 -0
- package/base-modules/discount-code/form.d.ts +1 -0
- package/base-modules/discount-code/form.js +44 -0
- package/base-modules/discount-code/more-actions.d.ts +9 -0
- package/base-modules/discount-code/more-actions.js +13 -0
- package/base-modules/discount-code/page.d.ts +16 -0
- package/base-modules/discount-code/page.js +120 -0
- package/base-modules/discount-code/validate.d.ts +19 -0
- package/base-modules/discount-code/validate.js +38 -0
- package/base-modules/discount-code/view.d.ts +1 -0
- package/base-modules/discount-code/view.js +26 -0
- package/base-modules/family/cache.d.ts +14 -0
- package/base-modules/family/cache.js +31 -0
- package/base-modules/family/constants.d.ts +22 -0
- package/base-modules/family/constants.js +26 -0
- package/base-modules/family/context.d.ts +173 -0
- package/base-modules/family/context.js +441 -0
- package/base-modules/family/filter.d.ts +1 -0
- package/base-modules/family/filter.js +28 -0
- package/base-modules/family/form.d.ts +1 -0
- package/base-modules/family/form.js +12 -0
- package/base-modules/family/more-actions.d.ts +1 -0
- package/base-modules/family/more-actions.js +5 -0
- package/base-modules/family/page.d.ts +16 -0
- package/base-modules/family/page.js +120 -0
- package/base-modules/family/validate.d.ts +15 -0
- package/base-modules/family/validate.js +18 -0
- package/base-modules/family/view.d.ts +1 -0
- package/base-modules/family/view.js +18 -0
- package/base-modules/family-member/cache.d.ts +14 -0
- package/base-modules/family-member/cache.js +31 -0
- package/base-modules/family-member/constants.d.ts +22 -0
- package/base-modules/family-member/constants.js +26 -0
- package/base-modules/family-member/context.d.ts +215 -0
- package/base-modules/family-member/context.js +486 -0
- package/base-modules/family-member/filter.d.ts +1 -0
- package/base-modules/family-member/filter.js +28 -0
- package/base-modules/family-member/form.d.ts +1 -0
- package/base-modules/family-member/form.js +17 -0
- package/base-modules/family-member/more-actions.d.ts +1 -0
- package/base-modules/family-member/more-actions.js +5 -0
- package/base-modules/family-member/page.d.ts +16 -0
- package/base-modules/family-member/page.js +122 -0
- package/base-modules/family-member/validate.d.ts +24 -0
- package/base-modules/family-member/validate.js +27 -0
- package/base-modules/family-member/view.d.ts +1 -0
- package/base-modules/family-member/view.js +40 -0
- package/base-modules/student-profile/cache.d.ts +14 -0
- package/base-modules/student-profile/cache.js +31 -0
- package/base-modules/student-profile/constants.d.ts +105 -0
- package/base-modules/student-profile/constants.js +132 -0
- package/base-modules/student-profile/context.d.ts +290 -0
- package/base-modules/student-profile/context.js +583 -0
- package/base-modules/student-profile/filter.d.ts +1 -0
- package/base-modules/student-profile/filter.js +26 -0
- package/base-modules/student-profile/form.d.ts +1 -0
- package/base-modules/student-profile/form.js +19 -0
- package/base-modules/student-profile/more-actions.d.ts +1 -0
- package/base-modules/student-profile/more-actions.js +5 -0
- package/base-modules/student-profile/page.d.ts +9 -0
- package/base-modules/student-profile/page.js +86 -0
- package/base-modules/student-profile/validate.d.ts +23 -0
- package/base-modules/student-profile/validate.js +34 -0
- package/base-modules/student-profile/view.d.ts +1 -0
- package/base-modules/student-profile/view.js +29 -0
- package/base-modules/workspace/cache.d.ts +9 -0
- package/base-modules/workspace/cache.js +28 -0
- package/base-modules/workspace/constants.d.ts +10 -0
- package/base-modules/workspace/constants.js +18 -0
- package/base-modules/workspace/context.d.ts +187 -0
- package/base-modules/workspace/context.js +293 -0
- package/base-modules/workspace/drawer.d.ts +1 -0
- package/base-modules/workspace/drawer.js +24 -0
- package/base-modules/workspace/filter.d.ts +1 -0
- package/base-modules/workspace/filter.js +13 -0
- package/base-modules/workspace/form.d.ts +1 -0
- package/base-modules/workspace/form.js +40 -0
- package/base-modules/workspace/more-actions.d.ts +1 -0
- package/base-modules/workspace/more-actions.js +13 -0
- package/base-modules/workspace/page.d.ts +1 -0
- package/base-modules/workspace/page.js +31 -0
- package/base-modules/workspace/validate.d.ts +9 -0
- package/base-modules/workspace/validate.js +8 -0
- package/base-modules/workspace/view.d.ts +1 -0
- package/base-modules/workspace/view.js +52 -0
- package/components/rbac-no-access.d.ts +6 -0
- package/components/rbac-no-access.js +4 -0
- package/constants.d.ts +81 -0
- package/constants.js +81 -0
- package/lib/utils.d.ts +2 -0
- package/lib/utils.js +5 -0
- package/package.json +104 -0
- package/tsconfig.build.tsbuildinfo +1 -0
- package/type.d.ts +1141 -0
- package/type.js +427 -0
- package/utils/admission-pdf.d.ts +78 -0
- package/utils/admission-pdf.js +73 -0
- package/utils/clear-cache.d.ts +1 -0
- package/utils/clear-cache.js +8 -0
- package/utils/format-value.d.ts +1 -0
- package/utils/format-value.js +1 -0
- package/utils/pdf-generator.d.ts +41 -0
- package/utils/pdf-generator.js +107 -0
- package/utils/resolve-rbac-permissions.d.ts +11 -0
- package/utils/resolve-rbac-permissions.js +251 -0
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
/**
|
|
4
|
+
* Discount Code Page Component
|
|
5
|
+
*
|
|
6
|
+
* Thin wrapper around GenericModulePage. All handlers, header actions, and row
|
|
7
|
+
* actions live in context.tsx — this file only owns:
|
|
8
|
+
* - tableBodyCols (static, module-level constant)
|
|
9
|
+
* - discountCodeConfig (memoised on locale change only; size fixed so the
|
|
10
|
+
* component type produced by createGenericModulePage never changes at
|
|
11
|
+
* runtime, preventing the infinite-remount re-render loop)
|
|
12
|
+
* - permission guard
|
|
13
|
+
*/
|
|
14
|
+
import { useMemo } from "react";
|
|
15
|
+
import { COMPONENT_TYPE } from "@appcorp/shadcn/components/enhanced-table";
|
|
16
|
+
import { createGenericModulePage, } from "@react-pakistan/util-functions/factory/generic-component-factory";
|
|
17
|
+
import { useDiscountCodeModule, DiscountCodeProvider, DISCOUNT_CODE_DRAWER, DISCOUNT_CODE_ACTION_TYPES, } from "./context";
|
|
18
|
+
import { DiscountCodeFilter } from "./filter";
|
|
19
|
+
import { DiscountCodeForm } from "./form";
|
|
20
|
+
import { DiscountCodeMoreActions } from "./more-actions";
|
|
21
|
+
import { DiscountCodeView } from "./view";
|
|
22
|
+
// import { useAuthStateContext } from "@/contexts/auth-context";
|
|
23
|
+
import { resolveRbacPermissions } from "@/utils/resolve-rbac-permissions";
|
|
24
|
+
import { RbacNoAccess } from "@/components/rbac-no-access";
|
|
25
|
+
import { useTranslations } from "next-intl";
|
|
26
|
+
// ============================================================================
|
|
27
|
+
// TABLE COLUMN CONFIGURATION (static — no runtime deps)
|
|
28
|
+
// ============================================================================
|
|
29
|
+
const tableBodyCols = [
|
|
30
|
+
{ componentType: COMPONENT_TYPE.ID, key: "id" },
|
|
31
|
+
{ componentType: COMPONENT_TYPE.BOLD_TEXT, key: "code" },
|
|
32
|
+
{ componentType: COMPONENT_TYPE.TEXT, key: "description" },
|
|
33
|
+
{ componentType: COMPONENT_TYPE.TEXT, key: "discountType" },
|
|
34
|
+
{ componentType: COMPONENT_TYPE.TEXT, key: "discountValue" },
|
|
35
|
+
{ componentType: COMPONENT_TYPE.BOOLEAN, key: "enabled" },
|
|
36
|
+
{ componentType: COMPONENT_TYPE.ACTIONS },
|
|
37
|
+
];
|
|
38
|
+
const tableColumns = [
|
|
39
|
+
{ label: "id", width: "5%" },
|
|
40
|
+
{ label: "code", width: "15%" },
|
|
41
|
+
{ label: "description", width: "25%" },
|
|
42
|
+
{ label: "discountType", width: "15%" },
|
|
43
|
+
{ label: "discountValue", width: "15%" },
|
|
44
|
+
{ label: "status", width: "15%" },
|
|
45
|
+
{ label: "actions", width: "10%" },
|
|
46
|
+
];
|
|
47
|
+
// ============================================================================
|
|
48
|
+
// TRANSLATED COLUMNS HELPER
|
|
49
|
+
// ============================================================================
|
|
50
|
+
const getTranslatedColumns = (t) => tableColumns.map((col) => (Object.assign(Object.assign({}, col), { label: t(col.label) })));
|
|
51
|
+
// ============================================================================
|
|
52
|
+
// COMPONENT FACTORY (creates JSX elements when config is created, not during render)
|
|
53
|
+
// ============================================================================
|
|
54
|
+
const createComponentInstances = () => ({
|
|
55
|
+
filter: _jsx(DiscountCodeFilter, {}),
|
|
56
|
+
form: _jsx(DiscountCodeForm, {}),
|
|
57
|
+
moreActions: _jsx(DiscountCodeMoreActions, {}),
|
|
58
|
+
view: _jsx(DiscountCodeView, {}),
|
|
59
|
+
});
|
|
60
|
+
// ============================================================================
|
|
61
|
+
// CONFIG CREATION HELPER
|
|
62
|
+
// ============================================================================
|
|
63
|
+
const createDiscountCodeConfig = (t, drawer, dispatch) => {
|
|
64
|
+
const components = createComponentInstances();
|
|
65
|
+
return {
|
|
66
|
+
moduleName: "discountCode",
|
|
67
|
+
tableColumns: getTranslatedColumns(t),
|
|
68
|
+
cancelLabel: t("cancel"),
|
|
69
|
+
drawerTitle: t("drawerTitle"),
|
|
70
|
+
filterContent: components.filter,
|
|
71
|
+
formContent: components.form,
|
|
72
|
+
moreActionsContent: components.moreActions,
|
|
73
|
+
saveLabel: t("save"),
|
|
74
|
+
searchPlaceholder: t("tableSearchPlaceholder"),
|
|
75
|
+
tableDescription: t("tableDescription"),
|
|
76
|
+
tableTitle: t("tableTitle"),
|
|
77
|
+
viewContent: components.view,
|
|
78
|
+
size: drawer === DISCOUNT_CODE_DRAWER.FORM_DRAWER ? "full" : "small",
|
|
79
|
+
onClearFilters: () => {
|
|
80
|
+
dispatch({ type: DISCOUNT_CODE_ACTION_TYPES.RESET_FORM });
|
|
81
|
+
},
|
|
82
|
+
};
|
|
83
|
+
};
|
|
84
|
+
// ============================================================================
|
|
85
|
+
// STABLE PAGE COMPONENT (created once, outside render)
|
|
86
|
+
// ============================================================================
|
|
87
|
+
const GenericDiscountCodePage = createGenericModulePage({
|
|
88
|
+
moduleName: "discountCode",
|
|
89
|
+
tableColumns: [],
|
|
90
|
+
cancelLabel: "",
|
|
91
|
+
drawerTitle: "",
|
|
92
|
+
filterContent: _jsx(DiscountCodeFilter, {}),
|
|
93
|
+
formContent: _jsx(DiscountCodeForm, {}),
|
|
94
|
+
moreActionsContent: _jsx(DiscountCodeMoreActions, {}),
|
|
95
|
+
saveLabel: "",
|
|
96
|
+
searchPlaceholder: "",
|
|
97
|
+
tableDescription: "",
|
|
98
|
+
tableTitle: "",
|
|
99
|
+
viewContent: _jsx(DiscountCodeView, {}),
|
|
100
|
+
size: "small",
|
|
101
|
+
onClearFilters: () => { },
|
|
102
|
+
});
|
|
103
|
+
// ============================================================================
|
|
104
|
+
// INNER PAGE (requires DiscountCodeProvider context)
|
|
105
|
+
// ============================================================================
|
|
106
|
+
const DiscountCodePageInner = ({ userRole }) => {
|
|
107
|
+
const t = useTranslations("discountCode");
|
|
108
|
+
const context = useDiscountCodeModule();
|
|
109
|
+
const hasPermission = useMemo(() => resolveRbacPermissions({
|
|
110
|
+
userRole,
|
|
111
|
+
moduleName: "DiscountCode",
|
|
112
|
+
}), [userRole]);
|
|
113
|
+
// Memoize config creation
|
|
114
|
+
const discountCodeConfig = useMemo(() => createDiscountCodeConfig(t, context.state.drawer, context.dispatch), [t, context.state.drawer, context.dispatch]);
|
|
115
|
+
if (!hasPermission) {
|
|
116
|
+
return _jsx(RbacNoAccess, { moduleName: "DiscountCode" });
|
|
117
|
+
}
|
|
118
|
+
return (_jsx("div", { className: "p-4", children: _jsx(GenericDiscountCodePage, { config: discountCodeConfig, context: context, tableBodyCols: tableBodyCols }) }));
|
|
119
|
+
};
|
|
120
|
+
export const DiscountCodePage = ({ userRole }) => (_jsx(DiscountCodeProvider, { children: _jsx(DiscountCodePageInner, { userRole: userRole }) }));
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Discount Code Validation Schema
|
|
3
|
+
*
|
|
4
|
+
* Zod validation schemas for discount code form data. The validation
|
|
5
|
+
* enforces field presence and type-specific constraints for `discountValue`:
|
|
6
|
+
* - Percentage values must be between 0 and 100
|
|
7
|
+
* - Fixed values must be a positive currency amount (example upper bound: 1000)
|
|
8
|
+
*
|
|
9
|
+
* Keep messages human-friendly as they are surfaced directly to the UI.
|
|
10
|
+
*/
|
|
11
|
+
import { z } from "zod";
|
|
12
|
+
import { DISCOUNT_TYPE } from "@/type";
|
|
13
|
+
export declare const accountDiscountCodeFormValidation: z.ZodObject<{
|
|
14
|
+
code: z.ZodString;
|
|
15
|
+
description: z.ZodOptional<z.ZodString>;
|
|
16
|
+
discountType: z.ZodEnum<typeof DISCOUNT_TYPE>;
|
|
17
|
+
discountValue: z.ZodNumber;
|
|
18
|
+
enabled: z.ZodOptional<z.ZodBoolean>;
|
|
19
|
+
}, z.core.$strip>;
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Discount Code Validation Schema
|
|
3
|
+
*
|
|
4
|
+
* Zod validation schemas for discount code form data. The validation
|
|
5
|
+
* enforces field presence and type-specific constraints for `discountValue`:
|
|
6
|
+
* - Percentage values must be between 0 and 100
|
|
7
|
+
* - Fixed values must be a positive currency amount (example upper bound: 1000)
|
|
8
|
+
*
|
|
9
|
+
* Keep messages human-friendly as they are surfaced directly to the UI.
|
|
10
|
+
*/
|
|
11
|
+
import { z } from "zod";
|
|
12
|
+
import { DISCOUNT_TYPE } from "@/type";
|
|
13
|
+
// ============================================================================
|
|
14
|
+
// VALIDATION SCHEMA
|
|
15
|
+
// ============================================================================
|
|
16
|
+
export const accountDiscountCodeFormValidation = z
|
|
17
|
+
.object({
|
|
18
|
+
code: z
|
|
19
|
+
.string()
|
|
20
|
+
.min(1, "Discount code is required")
|
|
21
|
+
.max(50, "Code must be less than 50 characters"),
|
|
22
|
+
description: z.string().optional(),
|
|
23
|
+
discountType: z.nativeEnum(DISCOUNT_TYPE),
|
|
24
|
+
discountValue: z.number(),
|
|
25
|
+
enabled: z.boolean().optional(),
|
|
26
|
+
})
|
|
27
|
+
.refine((data) => {
|
|
28
|
+
if (data.discountType === DISCOUNT_TYPE.PERCENTAGE) {
|
|
29
|
+
return data.discountValue >= 0 && data.discountValue <= 100;
|
|
30
|
+
}
|
|
31
|
+
else if (data.discountType === DISCOUNT_TYPE.FIXED) {
|
|
32
|
+
return data.discountValue > 0 && data.discountValue < 1000;
|
|
33
|
+
}
|
|
34
|
+
return true;
|
|
35
|
+
}, {
|
|
36
|
+
message: "Invalid discount value for the selected discount type",
|
|
37
|
+
path: ["discountValue"],
|
|
38
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const DiscountCodeView: () => import("react/jsx-runtime").JSX.Element;
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
3
|
+
/**
|
|
4
|
+
* Discount Code View — read-only details
|
|
5
|
+
*
|
|
6
|
+
* Rendered inside the module's view-drawer. The component reads the
|
|
7
|
+
* current form state from `useDiscountCodeModule()` and presents
|
|
8
|
+
* user-friendly labels and badges. Avoid side-effects here; fetching
|
|
9
|
+
* is handled by the context hook when opening details.
|
|
10
|
+
*/
|
|
11
|
+
import { useDiscountCodeModule } from "./context";
|
|
12
|
+
import { useTranslations } from "next-intl";
|
|
13
|
+
import { Card, CardContent, CardDescription, CardHeader, CardTitle, } from "@appcorp/shadcn/components/ui/card";
|
|
14
|
+
import { Badge } from "@appcorp/shadcn/components/ui/badge";
|
|
15
|
+
import { Separator } from "@appcorp/shadcn/components/ui/separator";
|
|
16
|
+
import { CheckCircle2, XCircle } from "lucide-react";
|
|
17
|
+
import { DISCOUNT_TYPE } from "@/type";
|
|
18
|
+
import { formatValue } from "@/utils/format-value";
|
|
19
|
+
export const DiscountCodeView = () => {
|
|
20
|
+
const { state } = useDiscountCodeModule();
|
|
21
|
+
const t = useTranslations("discountCode");
|
|
22
|
+
const { code, description, discountType, enabled } = state;
|
|
23
|
+
return (_jsx("div", { className: "space-y-6", children: _jsxs(Card, { children: [_jsxs(CardHeader, { children: [_jsx(CardTitle, { className: "flex items-center gap-2", children: t("viewTitle") }), _jsx(CardDescription, { children: t("viewDescription") })] }), _jsxs(CardContent, { className: "space-y-4", children: [_jsxs("div", { className: "grid grid-cols-1 md:grid-cols-2 gap-4", children: [_jsxs("div", { children: [_jsx("label", { className: "text-sm font-medium text-gray-700", children: t("viewLabelsDiscountCode") }), _jsx("p", { className: "mt-1 text-lg font-mono font-semibold", children: formatValue(code) })] }), _jsxs("div", { children: [_jsx("label", { className: "text-sm font-medium text-gray-700", children: t("viewLabelsStatus") }), _jsx("div", { className: "mt-1", children: _jsx(Badge, { variant: enabled ? "default" : "secondary", children: enabled ? (_jsxs(_Fragment, { children: [_jsx(CheckCircle2, { className: "h-3 w-3 mr-1" }), t("viewStatusEnabled")] })) : (_jsxs(_Fragment, { children: [_jsx(XCircle, { className: "h-3 w-3 mr-1" }), t("viewStatusDisabled")] })) }) })] }), _jsxs("div", { children: [_jsx("label", { className: "text-sm font-medium text-gray-700", children: t("viewLabelsDiscountType") }), _jsx("p", { className: "mt-1 text-gray-900 font-medium", children: discountType === DISCOUNT_TYPE.PERCENTAGE
|
|
24
|
+
? t("formDiscountTypeOptionsPercentage")
|
|
25
|
+
: t("formDiscountTypeOptionsFixed") })] }), _jsxs("div", { children: [_jsx("label", { className: "text-sm font-medium text-gray-700", children: t("viewLabelsDiscountValue") }), _jsx("p", { className: "mt-1 text-xl font-semibold text-primary" })] })] }), _jsx(Separator, {}), _jsxs("div", { children: [_jsx("label", { className: "text-sm font-medium text-gray-700", children: t("viewLabelsDescription") }), _jsx("p", { className: "mt-1 text-gray-900", children: formatValue(description) })] })] })] }) }));
|
|
26
|
+
};
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Family Module Cache Utilities
|
|
3
|
+
*
|
|
4
|
+
* Provides localStorage-based caching for families using generic cache system.
|
|
5
|
+
*/
|
|
6
|
+
import { FamilyBE } from "@/type";
|
|
7
|
+
export declare const getCachedFamiliesSync: () => import("@react-pakistan/util-functions").ListResponse<FamilyBE>;
|
|
8
|
+
export declare const getCachedFamilies: ({ params, }: {
|
|
9
|
+
params?: Record<string, unknown>;
|
|
10
|
+
}) => Promise<import("@react-pakistan/util-functions").ListResponse<FamilyBE>>;
|
|
11
|
+
export declare const getCachedFamilyById: (familyId: string) => FamilyBE | null;
|
|
12
|
+
export declare const invalidateFamiliesCache: () => void;
|
|
13
|
+
export declare const preloadFamilies: () => Promise<import("@react-pakistan/util-functions").ListResponse<FamilyBE>>;
|
|
14
|
+
export declare const isFamiliesCacheStale: () => boolean;
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Family Module Cache Utilities
|
|
3
|
+
*
|
|
4
|
+
* Provides localStorage-based caching for families using generic cache system.
|
|
5
|
+
*/
|
|
6
|
+
import { LS_KEYS } from "@/constants";
|
|
7
|
+
import { FAMILY_API_ROUTES } from "./constants";
|
|
8
|
+
import { getCachedData, getCachedDataSync, getCachedItemById, invalidateCache, isCacheStale, preloadCache, } from "@react-pakistan/util-functions";
|
|
9
|
+
// ============================================================================
|
|
10
|
+
// CACHE CONFIGURATION
|
|
11
|
+
// ============================================================================
|
|
12
|
+
const FAMILY_CACHE_CONFIG = {
|
|
13
|
+
cacheKey: LS_KEYS.FAMILIES,
|
|
14
|
+
apiUrl: FAMILY_API_ROUTES.UNIT,
|
|
15
|
+
};
|
|
16
|
+
// ============================================================================
|
|
17
|
+
// FAMILY-SPECIFIC CACHE FUNCTIONS
|
|
18
|
+
// ============================================================================
|
|
19
|
+
export const getCachedFamiliesSync = () => getCachedDataSync(LS_KEYS.FAMILIES);
|
|
20
|
+
export const getCachedFamilies = ({ params, }) => getCachedData({
|
|
21
|
+
config: FAMILY_CACHE_CONFIG,
|
|
22
|
+
params,
|
|
23
|
+
headers: {
|
|
24
|
+
"Content-Type": "application/json",
|
|
25
|
+
"x-api-token": process.env.NEXT_PUBLIC_API_KEY,
|
|
26
|
+
},
|
|
27
|
+
});
|
|
28
|
+
export const getCachedFamilyById = (familyId) => getCachedItemById(LS_KEYS.FAMILIES, familyId);
|
|
29
|
+
export const invalidateFamiliesCache = () => invalidateCache(LS_KEYS.FAMILIES);
|
|
30
|
+
export const preloadFamilies = () => preloadCache(FAMILY_CACHE_CONFIG);
|
|
31
|
+
export const isFamiliesCacheStale = () => isCacheStale(LS_KEYS.FAMILIES);
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Family Constants
|
|
3
|
+
*
|
|
4
|
+
* Organization:
|
|
5
|
+
* - Page Configuration
|
|
6
|
+
* - API Routes
|
|
7
|
+
* - Table Configuration
|
|
8
|
+
*/
|
|
9
|
+
export declare const pageLimit: number;
|
|
10
|
+
export declare const FAMILY_API_ROUTES: {
|
|
11
|
+
readonly UNIT: "/api/v1/family";
|
|
12
|
+
};
|
|
13
|
+
export declare const ENABLED_OPTIONS: readonly [{
|
|
14
|
+
readonly label: "All";
|
|
15
|
+
readonly value: "";
|
|
16
|
+
}, {
|
|
17
|
+
readonly label: "Enabled";
|
|
18
|
+
readonly value: "true";
|
|
19
|
+
}, {
|
|
20
|
+
readonly label: "Disabled";
|
|
21
|
+
readonly value: "false";
|
|
22
|
+
}];
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Family Constants
|
|
3
|
+
*
|
|
4
|
+
* Organization:
|
|
5
|
+
* - Page Configuration
|
|
6
|
+
* - API Routes
|
|
7
|
+
* - Table Configuration
|
|
8
|
+
*/
|
|
9
|
+
// ============================================================================
|
|
10
|
+
// PAGE CONFIGURATION
|
|
11
|
+
// ============================================================================
|
|
12
|
+
export const pageLimit = Number(process.env.NEXT_PUBLIC_PAGE_LIMIT) || 10;
|
|
13
|
+
// ============================================================================
|
|
14
|
+
// API ROUTES
|
|
15
|
+
// ============================================================================
|
|
16
|
+
export const FAMILY_API_ROUTES = {
|
|
17
|
+
UNIT: "/api/v1/family",
|
|
18
|
+
};
|
|
19
|
+
// ============================================================================
|
|
20
|
+
// ENABLED OPTIONS
|
|
21
|
+
// ============================================================================
|
|
22
|
+
export const ENABLED_OPTIONS = [
|
|
23
|
+
{ label: "All", value: "" },
|
|
24
|
+
{ label: "Enabled", value: "true" },
|
|
25
|
+
{ label: "Disabled", value: "false" },
|
|
26
|
+
];
|
|
@@ -0,0 +1,173 @@
|
|
|
1
|
+
import { FamilyBE } from "@/type";
|
|
2
|
+
import { TableRow, type RowAction } from "@appcorp/shadcn/components/enhanced-table";
|
|
3
|
+
export declare const FAMILY_DRAWER: {
|
|
4
|
+
readonly FILTER_DRAWER: string;
|
|
5
|
+
readonly FORM_DRAWER: string;
|
|
6
|
+
readonly MORE_ACTIONS_DRAWER: string;
|
|
7
|
+
readonly VIEW_DRAWER: string;
|
|
8
|
+
};
|
|
9
|
+
export declare const FAMILY_ACTION_TYPES: {
|
|
10
|
+
readonly RESET_FORM: "RESET_FORM";
|
|
11
|
+
readonly SET_CURRENT_PAGE: "SET_CURRENT_PAGE";
|
|
12
|
+
readonly SET_PAGE_LIMIT: "SET_PAGE_LIMIT";
|
|
13
|
+
readonly SET_SEARCH_QUERY: "SET_SEARCH_QUERY";
|
|
14
|
+
readonly SET_DRAWER: "SET_DRAWER";
|
|
15
|
+
readonly SET_ITEMS: "SET_ITEMS";
|
|
16
|
+
readonly SET_FORM_DATA: "SET_FORM_DATA";
|
|
17
|
+
readonly SET_DISABLE_SAVE_BUTTON: "SET_DISABLE_SAVE_BUTTON";
|
|
18
|
+
readonly SET_INPUT_FIELD: "SET_INPUT_FIELD";
|
|
19
|
+
readonly SET_ERRORS: "SET_ERRORS";
|
|
20
|
+
readonly SET_FILTERS: "SET_FILTERS";
|
|
21
|
+
}, familyModuleConfig: import("@react-pakistan/util-functions/factory/generic-module-factory").ModuleConfig<{
|
|
22
|
+
items: FamilyBE[];
|
|
23
|
+
count: number;
|
|
24
|
+
currentPage: number;
|
|
25
|
+
pageLimit: number;
|
|
26
|
+
searchQuery: string;
|
|
27
|
+
disableSaveButton: boolean;
|
|
28
|
+
drawer: string | null;
|
|
29
|
+
address: string;
|
|
30
|
+
city: string;
|
|
31
|
+
country: string;
|
|
32
|
+
enabled: boolean;
|
|
33
|
+
errors: Record<string, string>;
|
|
34
|
+
familyCode: string;
|
|
35
|
+
filterEnabled: boolean | undefined;
|
|
36
|
+
id: string;
|
|
37
|
+
postalCode: string;
|
|
38
|
+
stateProvince: string;
|
|
39
|
+
userId: string;
|
|
40
|
+
}>, initialFamilyState: {
|
|
41
|
+
items: FamilyBE[];
|
|
42
|
+
count: number;
|
|
43
|
+
currentPage: number;
|
|
44
|
+
pageLimit: number;
|
|
45
|
+
searchQuery: string;
|
|
46
|
+
disableSaveButton: boolean;
|
|
47
|
+
drawer: string | null;
|
|
48
|
+
address: string;
|
|
49
|
+
city: string;
|
|
50
|
+
country: string;
|
|
51
|
+
enabled: boolean;
|
|
52
|
+
errors: Record<string, string>;
|
|
53
|
+
familyCode: string;
|
|
54
|
+
filterEnabled: boolean | undefined;
|
|
55
|
+
id: string;
|
|
56
|
+
postalCode: string;
|
|
57
|
+
stateProvince: string;
|
|
58
|
+
userId: string;
|
|
59
|
+
}, FamilyProvider: import("react").FC<{
|
|
60
|
+
children: React.ReactNode;
|
|
61
|
+
}>, familyReducer: (state: {
|
|
62
|
+
items: FamilyBE[];
|
|
63
|
+
count: number;
|
|
64
|
+
currentPage: number;
|
|
65
|
+
pageLimit: number;
|
|
66
|
+
searchQuery: string;
|
|
67
|
+
disableSaveButton: boolean;
|
|
68
|
+
drawer: string | null;
|
|
69
|
+
address: string;
|
|
70
|
+
city: string;
|
|
71
|
+
country: string;
|
|
72
|
+
enabled: boolean;
|
|
73
|
+
errors: Record<string, string>;
|
|
74
|
+
familyCode: string;
|
|
75
|
+
filterEnabled: boolean | undefined;
|
|
76
|
+
id: string;
|
|
77
|
+
postalCode: string;
|
|
78
|
+
stateProvince: string;
|
|
79
|
+
userId: string;
|
|
80
|
+
}, action: any) => {
|
|
81
|
+
items: FamilyBE[];
|
|
82
|
+
count: number;
|
|
83
|
+
currentPage: number;
|
|
84
|
+
pageLimit: number;
|
|
85
|
+
searchQuery: string;
|
|
86
|
+
disableSaveButton: boolean;
|
|
87
|
+
drawer: string | null;
|
|
88
|
+
address: string;
|
|
89
|
+
city: string;
|
|
90
|
+
country: string;
|
|
91
|
+
enabled: boolean;
|
|
92
|
+
errors: Record<string, string>;
|
|
93
|
+
familyCode: string;
|
|
94
|
+
filterEnabled: boolean | undefined;
|
|
95
|
+
id: string;
|
|
96
|
+
postalCode: string;
|
|
97
|
+
stateProvince: string;
|
|
98
|
+
userId: string;
|
|
99
|
+
}, useFamilyContext: () => import("@react-pakistan/util-functions/factory/generic-module-factory").GenericModuleContext<{
|
|
100
|
+
items: FamilyBE[];
|
|
101
|
+
count: number;
|
|
102
|
+
currentPage: number;
|
|
103
|
+
pageLimit: number;
|
|
104
|
+
searchQuery: string;
|
|
105
|
+
disableSaveButton: boolean;
|
|
106
|
+
drawer: string | null;
|
|
107
|
+
address: string;
|
|
108
|
+
city: string;
|
|
109
|
+
country: string;
|
|
110
|
+
enabled: boolean;
|
|
111
|
+
errors: Record<string, string>;
|
|
112
|
+
familyCode: string;
|
|
113
|
+
filterEnabled: boolean | undefined;
|
|
114
|
+
id: string;
|
|
115
|
+
postalCode: string;
|
|
116
|
+
stateProvince: string;
|
|
117
|
+
userId: string;
|
|
118
|
+
}>;
|
|
119
|
+
/**
|
|
120
|
+
* Backward-compatible alias used by dashboard-providers.tsx
|
|
121
|
+
*/
|
|
122
|
+
export declare const FamilyStateContextProvider: import("react").FC<{
|
|
123
|
+
children: React.ReactNode;
|
|
124
|
+
}>;
|
|
125
|
+
export declare const useFamilyModule: () => {
|
|
126
|
+
applyFilters: () => void;
|
|
127
|
+
byIdLoading: boolean;
|
|
128
|
+
clearFilters: () => void;
|
|
129
|
+
deleteLoading: boolean;
|
|
130
|
+
handleChange: (field: string, value: string | number | boolean | undefined | null) => void;
|
|
131
|
+
handleCloseDrawer: () => void;
|
|
132
|
+
handleCreate: () => void;
|
|
133
|
+
handleDelete: (row?: TableRow) => void;
|
|
134
|
+
handleEdit: (row?: TableRow) => void;
|
|
135
|
+
handleFilters: () => void;
|
|
136
|
+
handleMoreActions: () => void;
|
|
137
|
+
handlePageChange: (page: number) => void;
|
|
138
|
+
handlePageLimitChange: (limit: number) => void;
|
|
139
|
+
handleSearch: (query: string) => void;
|
|
140
|
+
handleSubmit: () => void;
|
|
141
|
+
handleView: (row?: TableRow) => void;
|
|
142
|
+
headerActions: {
|
|
143
|
+
enabled: boolean;
|
|
144
|
+
handleOnClick: () => void;
|
|
145
|
+
label: string;
|
|
146
|
+
order: number;
|
|
147
|
+
icon: import("react").ForwardRefExoticComponent<Omit<import("lucide-react").LucideProps, "ref"> & import("react").RefAttributes<SVGSVGElement>>;
|
|
148
|
+
}[];
|
|
149
|
+
listLoading: boolean;
|
|
150
|
+
rowActions: RowAction[];
|
|
151
|
+
updateLoading: boolean;
|
|
152
|
+
state: {
|
|
153
|
+
items: FamilyBE[];
|
|
154
|
+
count: number;
|
|
155
|
+
currentPage: number;
|
|
156
|
+
pageLimit: number;
|
|
157
|
+
searchQuery: string;
|
|
158
|
+
disableSaveButton: boolean;
|
|
159
|
+
drawer: string | null;
|
|
160
|
+
address: string;
|
|
161
|
+
city: string;
|
|
162
|
+
country: string;
|
|
163
|
+
enabled: boolean;
|
|
164
|
+
errors: Record<string, string>;
|
|
165
|
+
familyCode: string;
|
|
166
|
+
filterEnabled: boolean | undefined;
|
|
167
|
+
id: string;
|
|
168
|
+
postalCode: string;
|
|
169
|
+
stateProvince: string;
|
|
170
|
+
userId: string;
|
|
171
|
+
};
|
|
172
|
+
dispatch: React.Dispatch<any>;
|
|
173
|
+
};
|