@nestjs-dash/design-system 0.2.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/components/admin-shell.d.ts +48 -0
- package/dist/components/admin-shell.d.ts.map +1 -0
- package/dist/components/admin-shell.js +49 -0
- package/dist/components/admin-shell.js.map +1 -0
- package/dist/components/chart.d.ts +12 -0
- package/dist/components/chart.d.ts.map +1 -0
- package/dist/components/chart.js +68 -0
- package/dist/components/chart.js.map +1 -0
- package/dist/components/confirm-dialog.d.ts +17 -0
- package/dist/components/confirm-dialog.d.ts.map +1 -0
- package/dist/components/confirm-dialog.js +8 -0
- package/dist/components/confirm-dialog.js.map +1 -0
- package/dist/components/data-pagination.d.ts +13 -0
- package/dist/components/data-pagination.d.ts.map +1 -0
- package/dist/components/data-pagination.js +61 -0
- package/dist/components/data-pagination.js.map +1 -0
- package/dist/components/data-table.d.ts +27 -0
- package/dist/components/data-table.d.ts.map +1 -0
- package/dist/components/data-table.js +82 -0
- package/dist/components/data-table.js.map +1 -0
- package/dist/components/empty-state.d.ts +5 -0
- package/dist/components/empty-state.d.ts.map +1 -0
- package/dist/components/empty-state.js +5 -0
- package/dist/components/empty-state.js.map +1 -0
- package/dist/components/file-upload-field.d.ts +28 -0
- package/dist/components/file-upload-field.d.ts.map +1 -0
- package/dist/components/file-upload-field.js +104 -0
- package/dist/components/file-upload-field.js.map +1 -0
- package/dist/components/icon.d.ts +8 -0
- package/dist/components/icon.d.ts.map +1 -0
- package/dist/components/icon.js +21 -0
- package/dist/components/icon.js.map +1 -0
- package/dist/components/image-placeholder.d.ts +7 -0
- package/dist/components/image-placeholder.d.ts.map +1 -0
- package/dist/components/image-placeholder.js +11 -0
- package/dist/components/image-placeholder.js.map +1 -0
- package/dist/components/image-upload-field.d.ts +29 -0
- package/dist/components/image-upload-field.d.ts.map +1 -0
- package/dist/components/image-upload-field.js +103 -0
- package/dist/components/image-upload-field.js.map +1 -0
- package/dist/components/repeater-field.d.ts +18 -0
- package/dist/components/repeater-field.d.ts.map +1 -0
- package/dist/components/repeater-field.js +104 -0
- package/dist/components/repeater-field.js.map +1 -0
- package/dist/components/rich-box-field.d.ts +29 -0
- package/dist/components/rich-box-field.d.ts.map +1 -0
- package/dist/components/rich-box-field.js +69 -0
- package/dist/components/rich-box-field.js.map +1 -0
- package/dist/components/rich-editor-field.d.ts +15 -0
- package/dist/components/rich-editor-field.d.ts.map +1 -0
- package/dist/components/rich-editor-field.js +52 -0
- package/dist/components/rich-editor-field.js.map +1 -0
- package/dist/components/schema-form.d.ts +42 -0
- package/dist/components/schema-form.d.ts.map +1 -0
- package/dist/components/schema-form.js +180 -0
- package/dist/components/schema-form.js.map +1 -0
- package/dist/components/tags-input-field.d.ts +14 -0
- package/dist/components/tags-input-field.d.ts.map +1 -0
- package/dist/components/tags-input-field.js +59 -0
- package/dist/components/tags-input-field.js.map +1 -0
- package/dist/components/theme-toggle.d.ts +12 -0
- package/dist/components/theme-toggle.d.ts.map +1 -0
- package/dist/components/theme-toggle.js +19 -0
- package/dist/components/theme-toggle.js.map +1 -0
- package/dist/components/ui/alert.d.ts +10 -0
- package/dist/components/ui/alert.d.ts.map +1 -0
- package/dist/components/ui/alert.js +26 -0
- package/dist/components/ui/alert.js.map +1 -0
- package/dist/components/ui/avatar.d.ts +12 -0
- package/dist/components/ui/avatar.d.ts.map +1 -0
- package/dist/components/ui/avatar.js +25 -0
- package/dist/components/ui/avatar.js.map +1 -0
- package/dist/components/ui/badge.d.ts +10 -0
- package/dist/components/ui/badge.d.ts.map +1 -0
- package/dist/components/ui/badge.js +26 -0
- package/dist/components/ui/badge.js.map +1 -0
- package/dist/components/ui/breadcrumb.d.ts +12 -0
- package/dist/components/ui/breadcrumb.d.ts.map +1 -0
- package/dist/components/ui/breadcrumb.js +29 -0
- package/dist/components/ui/breadcrumb.js.map +1 -0
- package/dist/components/ui/button.d.ts +11 -0
- package/dist/components/ui/button.d.ts.map +1 -0
- package/dist/components/ui/button.js +39 -0
- package/dist/components/ui/button.js.map +1 -0
- package/dist/components/ui/card.d.ts +10 -0
- package/dist/components/ui/card.d.ts.map +1 -0
- package/dist/components/ui/card.js +26 -0
- package/dist/components/ui/card.js.map +1 -0
- package/dist/components/ui/checkbox.d.ts +5 -0
- package/dist/components/ui/checkbox.d.ts.map +1 -0
- package/dist/components/ui/checkbox.js +10 -0
- package/dist/components/ui/checkbox.js.map +1 -0
- package/dist/components/ui/collapsible.d.ts +6 -0
- package/dist/components/ui/collapsible.d.ts.map +1 -0
- package/dist/components/ui/collapsible.js +13 -0
- package/dist/components/ui/collapsible.js.map +1 -0
- package/dist/components/ui/dialog.d.ts +18 -0
- package/dist/components/ui/dialog.d.ts.map +1 -0
- package/dist/components/ui/dialog.js +39 -0
- package/dist/components/ui/dialog.js.map +1 -0
- package/dist/components/ui/dropdown-menu.d.ts +26 -0
- package/dist/components/ui/dropdown-menu.d.ts.map +1 -0
- package/dist/components/ui/dropdown-menu.js +53 -0
- package/dist/components/ui/dropdown-menu.js.map +1 -0
- package/dist/components/ui/input.d.ts +4 -0
- package/dist/components/ui/input.d.ts.map +1 -0
- package/dist/components/ui/input.js +8 -0
- package/dist/components/ui/input.js.map +1 -0
- package/dist/components/ui/label.d.ts +5 -0
- package/dist/components/ui/label.d.ts.map +1 -0
- package/dist/components/ui/label.js +9 -0
- package/dist/components/ui/label.js.map +1 -0
- package/dist/components/ui/pagination.d.ts +14 -0
- package/dist/components/ui/pagination.d.ts.map +1 -0
- package/dist/components/ui/pagination.js +31 -0
- package/dist/components/ui/pagination.js.map +1 -0
- package/dist/components/ui/scroll-area.d.ts +6 -0
- package/dist/components/ui/scroll-area.d.ts.map +1 -0
- package/dist/components/ui/scroll-area.js +13 -0
- package/dist/components/ui/scroll-area.js.map +1 -0
- package/dist/components/ui/select.d.ts +16 -0
- package/dist/components/ui/select.d.ts.map +1 -0
- package/dist/components/ui/select.js +40 -0
- package/dist/components/ui/select.js.map +1 -0
- package/dist/components/ui/separator.d.ts +5 -0
- package/dist/components/ui/separator.d.ts.map +1 -0
- package/dist/components/ui/separator.js +10 -0
- package/dist/components/ui/separator.js.map +1 -0
- package/dist/components/ui/sheet.d.ts +15 -0
- package/dist/components/ui/sheet.d.ts.map +1 -0
- package/dist/components/ui/sheet.js +41 -0
- package/dist/components/ui/sheet.js.map +1 -0
- package/dist/components/ui/sidebar.d.ts +70 -0
- package/dist/components/ui/sidebar.d.ts.map +1 -0
- package/dist/components/ui/sidebar.js +203 -0
- package/dist/components/ui/sidebar.js.map +1 -0
- package/dist/components/ui/skeleton.d.ts +3 -0
- package/dist/components/ui/skeleton.d.ts.map +1 -0
- package/dist/components/ui/skeleton.js +7 -0
- package/dist/components/ui/skeleton.js.map +1 -0
- package/dist/components/ui/table.d.ts +11 -0
- package/dist/components/ui/table.d.ts.map +1 -0
- package/dist/components/ui/table.js +30 -0
- package/dist/components/ui/table.js.map +1 -0
- package/dist/components/ui/tabs.d.ts +12 -0
- package/dist/components/ui/tabs.d.ts.map +1 -0
- package/dist/components/ui/tabs.js +34 -0
- package/dist/components/ui/tabs.js.map +1 -0
- package/dist/components/ui/textarea.d.ts +4 -0
- package/dist/components/ui/textarea.d.ts.map +1 -0
- package/dist/components/ui/textarea.js +8 -0
- package/dist/components/ui/textarea.js.map +1 -0
- package/dist/components/ui/tooltip.d.ts +8 -0
- package/dist/components/ui/tooltip.d.ts.map +1 -0
- package/dist/components/ui/tooltip.js +18 -0
- package/dist/components/ui/tooltip.js.map +1 -0
- package/dist/hooks/use-mobile.d.ts +2 -0
- package/dist/hooks/use-mobile.d.ts.map +1 -0
- package/dist/hooks/use-mobile.js +18 -0
- package/dist/hooks/use-mobile.js.map +1 -0
- package/dist/index.d.ts +45 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +44 -0
- package/dist/index.js.map +1 -0
- package/dist/lib/badge-colors.d.ts +4 -0
- package/dist/lib/badge-colors.d.ts.map +1 -0
- package/dist/lib/badge-colors.js +22 -0
- package/dist/lib/badge-colors.js.map +1 -0
- package/dist/lib/format-date.d.ts +7 -0
- package/dist/lib/format-date.d.ts.map +1 -0
- package/dist/lib/format-date.js +35 -0
- package/dist/lib/format-date.js.map +1 -0
- package/dist/lib/utils.d.ts +2 -0
- package/dist/lib/utils.d.ts.map +1 -0
- package/dist/lib/utils.js +2 -0
- package/dist/lib/utils.js.map +1 -0
- package/dist/nestjs-dash.css +2 -0
- package/dist/pagination.d.ts +10 -0
- package/dist/pagination.d.ts.map +1 -0
- package/dist/pagination.js +42 -0
- package/dist/pagination.js.map +1 -0
- package/dist/ui.d.ts +99 -0
- package/dist/ui.d.ts.map +1 -0
- package/dist/ui.js +104 -0
- package/dist/ui.js.map +1 -0
- package/package.json +81 -0
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import type { SchemaNode } from '@nestjs-dash/support';
|
|
2
|
+
import type { ReactNode } from 'react';
|
|
3
|
+
import type { PaginationMeta } from './data-pagination.js';
|
|
4
|
+
export interface NavigationItem {
|
|
5
|
+
label: string;
|
|
6
|
+
slug: string;
|
|
7
|
+
href: string;
|
|
8
|
+
icon?: string;
|
|
9
|
+
type?: string;
|
|
10
|
+
openInNewTab?: boolean;
|
|
11
|
+
}
|
|
12
|
+
export interface NavigationGroup {
|
|
13
|
+
label: string;
|
|
14
|
+
collapsible?: boolean;
|
|
15
|
+
collapsed?: boolean;
|
|
16
|
+
items: NavigationItem[];
|
|
17
|
+
}
|
|
18
|
+
export interface BreadcrumbItemModel {
|
|
19
|
+
label: string;
|
|
20
|
+
href?: string;
|
|
21
|
+
}
|
|
22
|
+
export interface PanelViewModel {
|
|
23
|
+
brandName: string;
|
|
24
|
+
path: string;
|
|
25
|
+
navigation: NavigationItem[];
|
|
26
|
+
navigationGroups?: NavigationGroup[];
|
|
27
|
+
breadcrumbs?: BreadcrumbItemModel[];
|
|
28
|
+
currentSlug?: string | null;
|
|
29
|
+
resource?: {
|
|
30
|
+
slug: string;
|
|
31
|
+
label: string;
|
|
32
|
+
table?: {
|
|
33
|
+
columns: SchemaNode[];
|
|
34
|
+
actions: SchemaNode[];
|
|
35
|
+
} | null;
|
|
36
|
+
form?: SchemaNode | null;
|
|
37
|
+
};
|
|
38
|
+
records?: Array<Record<string, unknown>>;
|
|
39
|
+
meta?: PaginationMeta;
|
|
40
|
+
}
|
|
41
|
+
export declare function AdminShell(props: {
|
|
42
|
+
model: PanelViewModel;
|
|
43
|
+
children?: ReactNode;
|
|
44
|
+
header?: ReactNode;
|
|
45
|
+
/** Called when a viewer expands/collapses a named nav group (accordion state). */
|
|
46
|
+
onGroupToggle?: (label: string, expanded: boolean) => void;
|
|
47
|
+
}): import("react").JSX.Element;
|
|
48
|
+
//# sourceMappingURL=admin-shell.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"admin-shell.d.ts","sourceRoot":"","sources":["../../src/components/admin-shell.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,sBAAsB,CAAC;AACvD,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AACvC,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAgC3D,MAAM,WAAW,cAAc;IAC7B,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,YAAY,CAAC,EAAE,OAAO,CAAC;CACxB;AAED,MAAM,WAAW,eAAe;IAC9B,KAAK,EAAE,MAAM,CAAC;IACd,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,KAAK,EAAE,cAAc,EAAE,CAAC;CACzB;AAED,MAAM,WAAW,mBAAmB;IAClC,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,cAAc;IAC7B,SAAS,EAAE,MAAM,CAAC;IAClB,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,EAAE,cAAc,EAAE,CAAC;IAC7B,gBAAgB,CAAC,EAAE,eAAe,EAAE,CAAC;IACrC,WAAW,CAAC,EAAE,mBAAmB,EAAE,CAAC;IACpC,WAAW,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,QAAQ,CAAC,EAAE;QACT,IAAI,EAAE,MAAM,CAAC;QACb,KAAK,EAAE,MAAM,CAAC;QACd,KAAK,CAAC,EAAE;YACN,OAAO,EAAE,UAAU,EAAE,CAAC;YACtB,OAAO,EAAE,UAAU,EAAE,CAAC;SACvB,GAAG,IAAI,CAAC;QACT,IAAI,CAAC,EAAE,UAAU,GAAG,IAAI,CAAC;KAC1B,CAAC;IACF,OAAO,CAAC,EAAE,KAAK,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;IACzC,IAAI,CAAC,EAAE,cAAc,CAAC;CACvB;AAQD,wBAAgB,UAAU,CAAC,KAAK,EAAE;IAChC,KAAK,EAAE,cAAc,CAAC;IACtB,QAAQ,CAAC,EAAE,SAAS,CAAC;IACrB,MAAM,CAAC,EAAE,SAAS,CAAC;IACnB,kFAAkF;IAClF,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,KAAK,IAAI,CAAC;CAC5D,+BA4LA"}
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
+
import { DataTable } from './data-table.js';
|
|
3
|
+
import { EmptyState } from './empty-state.js';
|
|
4
|
+
import { Icon } from './icon.js';
|
|
5
|
+
import { Breadcrumb, BreadcrumbItem, BreadcrumbLink, BreadcrumbList, BreadcrumbPage, BreadcrumbSeparator, } from './ui/breadcrumb.js';
|
|
6
|
+
import { Card, CardContent, CardHeader, CardTitle } from './ui/card.js';
|
|
7
|
+
import { Collapsible, CollapsibleContent, CollapsibleTrigger } from './ui/collapsible.js';
|
|
8
|
+
import { Separator } from './ui/separator.js';
|
|
9
|
+
import { Sidebar, SidebarContent, SidebarGroup, SidebarGroupContent, SidebarGroupLabel, SidebarHeader, SidebarInset, SidebarMenu, SidebarMenuButton, SidebarMenuItem, SidebarProvider, SidebarRail, SidebarTrigger, } from './ui/sidebar.js';
|
|
10
|
+
import { TooltipProvider } from './ui/tooltip.js';
|
|
11
|
+
function isCurrent(item, currentSlug) {
|
|
12
|
+
return (item.slug === currentSlug || (item.type === 'page' && currentSlug === `pages:${item.slug}`));
|
|
13
|
+
}
|
|
14
|
+
export function AdminShell(props) {
|
|
15
|
+
const listHrefBuilder = props.model.resource && props.model.path
|
|
16
|
+
? (page, limit) => {
|
|
17
|
+
const params = new URLSearchParams();
|
|
18
|
+
params.set('page', String(page));
|
|
19
|
+
params.set('limit', String(limit));
|
|
20
|
+
return `${props.model.path}/${props.model.resource.slug}?${params.toString()}`;
|
|
21
|
+
}
|
|
22
|
+
: undefined;
|
|
23
|
+
const body = props.children ??
|
|
24
|
+
(props.model.resource ? (_jsxs(Card, { children: [_jsx(CardHeader, { children: _jsx(CardTitle, { children: props.model.resource.label }) }), _jsx(CardContent, { children: props.model.resource.table ? (_jsx(DataTable, { columns: props.model.resource.table.columns, rows: props.model.records ?? [], meta: props.model.meta, buildHref: listHrefBuilder })) : null })] })) : (_jsx(EmptyState, { title: "Select a resource", description: "Choose an item from the sidebar." })));
|
|
25
|
+
const groups = props.model.navigationGroups;
|
|
26
|
+
const flatItems = props.model.navigation;
|
|
27
|
+
return (_jsx(TooltipProvider, { children: _jsxs(SidebarProvider, { defaultOpen: true, children: [_jsxs(Sidebar, { collapsible: "icon", variant: "sidebar", children: [_jsx(SidebarHeader, { className: "px-4 py-4 text-lg font-bold", children: _jsx("a", { href: props.model.path, className: "text-inherit no-underline", children: props.model.brandName }) }), _jsx(Separator, {}), _jsxs(SidebarContent, { children: [_jsx(SidebarGroup, { children: _jsx(SidebarGroupContent, { children: _jsx(SidebarMenu, { children: _jsx(SidebarMenuItem, { children: _jsx(SidebarMenuButton, { asChild: true, isActive: props.model.currentSlug == null, tooltip: "Dashboard", children: _jsx("a", { href: props.model.path, "aria-current": props.model.currentSlug == null ? 'page' : undefined, children: _jsx("span", { children: "Dashboard" }) }) }) }) }) }) }), groups?.length ? (groups.map((group) => {
|
|
28
|
+
const items = (_jsx(SidebarMenu, { children: group.items.map((item) => {
|
|
29
|
+
const current = isCurrent(item, props.model.currentSlug);
|
|
30
|
+
return (_jsx(SidebarMenuItem, { children: _jsx(SidebarMenuButton, { asChild: true, isActive: current, tooltip: item.label, children: _jsxs("a", { href: item.href, target: item.openInNewTab ? '_blank' : undefined, rel: item.openInNewTab ? 'noreferrer' : undefined, "aria-current": current ? 'page' : undefined, children: [item.icon ? _jsx(Icon, { name: item.icon }) : null, _jsx("span", { children: item.label })] }) }) }, item.slug));
|
|
31
|
+
}) }));
|
|
32
|
+
if (group.label === 'Main' || !group.collapsible) {
|
|
33
|
+
return (_jsxs(SidebarGroup, { children: [group.label !== 'Main' ? (_jsx(SidebarGroupLabel, { children: group.label })) : null, _jsx(SidebarGroupContent, { children: items })] }, group.label));
|
|
34
|
+
}
|
|
35
|
+
return (_jsx(Collapsible, { defaultOpen: !group.collapsed, onOpenChange: (open) => props.onGroupToggle?.(group.label, open), className: "group/nav-group", children: _jsxs(SidebarGroup, { children: [_jsx(CollapsibleTrigger, { asChild: true, children: _jsxs(SidebarGroupLabel, { className: "flex w-full cursor-pointer items-center justify-between", children: [group.label, _jsx(Icon, { name: "chevron-right", className: "transition-transform group-data-[state=open]/nav-group:rotate-90" })] }) }), _jsx(CollapsibleContent, { children: _jsx(SidebarGroupContent, { children: items }) })] }) }, group.label));
|
|
36
|
+
})) : (_jsx(SidebarGroup, { children: _jsx(SidebarGroupContent, { children: _jsx(SidebarMenu, { children: flatItems.map((item) => {
|
|
37
|
+
const current = isCurrent(item, props.model.currentSlug);
|
|
38
|
+
return (_jsx(SidebarMenuItem, { children: _jsx(SidebarMenuButton, { asChild: true, isActive: current, tooltip: item.label, children: _jsxs("a", { href: item.href, "aria-current": current ? 'page' : undefined, children: [item.icon ? _jsx(Icon, { name: item.icon }) : null, _jsx("span", { children: item.label })] }) }) }, item.slug));
|
|
39
|
+
}) }) }) }))] }), _jsx(SidebarRail, {})] }), _jsxs(SidebarInset, { children: [_jsxs("header", { className: "flex h-12 items-center gap-2 border-b border-border px-4", children: [_jsx(SidebarTrigger, {}), props.model.breadcrumbs?.length ? (_jsxs(_Fragment, { children: [_jsx(Separator, { orientation: "vertical", className: "mr-2 h-4" }), _jsx(Breadcrumb, { "data-afi-breadcrumbs": true, children: _jsx(BreadcrumbList, { children: props.model.breadcrumbs.flatMap((item, index) => {
|
|
40
|
+
const isLast = index === props.model.breadcrumbs.length - 1;
|
|
41
|
+
const nodes = [];
|
|
42
|
+
if (index > 0) {
|
|
43
|
+
nodes.push(_jsx(BreadcrumbSeparator, {}, `sep-${index}`));
|
|
44
|
+
}
|
|
45
|
+
nodes.push(_jsx(BreadcrumbItem, { children: isLast || !item.href ? (_jsx(BreadcrumbPage, { children: item.label })) : (_jsx(BreadcrumbLink, { href: item.href, children: item.label })) }, `${item.label}-${index}`));
|
|
46
|
+
return nodes;
|
|
47
|
+
}) }) })] })) : null, props.header ? _jsx("div", { className: "ml-auto flex items-center gap-2", children: props.header }) : null] }), _jsx("main", { className: "flex-1 p-6 space-y-4", children: body })] })] }) }));
|
|
48
|
+
}
|
|
49
|
+
//# sourceMappingURL=admin-shell.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"admin-shell.js","sourceRoot":"","sources":["../../src/components/admin-shell.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { ChartSpec } from '@nestjs-dash/support';
|
|
2
|
+
import * as React from 'react';
|
|
3
|
+
/**
|
|
4
|
+
* Renders a `ChartSpec` (produced by `@nestjs-dash/core`'s `BarChart`/
|
|
5
|
+
* `LineChart`/`PieChart` builders) as a real, hydrated, interactive Recharts
|
|
6
|
+
* component — colored via the design system's existing `--chart-1..5`
|
|
7
|
+
* theme tokens.
|
|
8
|
+
*/
|
|
9
|
+
export declare function ChartWidget({ spec }: {
|
|
10
|
+
spec: ChartSpec;
|
|
11
|
+
}): React.JSX.Element;
|
|
12
|
+
//# sourceMappingURL=chart.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chart.d.ts","sourceRoot":"","sources":["../../src/components/chart.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAA6B,SAAS,EAAE,MAAM,sBAAsB,CAAC;AACjF,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAgK/B;;;;;GAKG;AACH,wBAAgB,WAAW,CAAC,EAAE,IAAI,EAAE,EAAE;IAAE,IAAI,EAAE,SAAS,CAAA;CAAE,qBA6CxD"}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import * as React from 'react';
|
|
3
|
+
import { Bar, CartesianGrid, Legend, Line, Pie, BarChart as RBarChart, LineChart as RLineChart, PieChart as RPieChart, ResponsiveContainer, Tooltip, XAxis, YAxis, } from 'recharts';
|
|
4
|
+
import { EmptyState } from './empty-state.js';
|
|
5
|
+
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from './ui/card.js';
|
|
6
|
+
import { Skeleton } from './ui/skeleton.js';
|
|
7
|
+
/** `--chart-1..5` — the design system's existing shadcn-style chart color tokens. */
|
|
8
|
+
function chartColorVar(n) {
|
|
9
|
+
return `var(--chart-${n})`;
|
|
10
|
+
}
|
|
11
|
+
function seriesColor(series, index) {
|
|
12
|
+
return chartColorVar(series.color ?? ((index % 5) + 1));
|
|
13
|
+
}
|
|
14
|
+
const subscribeNever = () => () => { };
|
|
15
|
+
/** True once running on the client, false during SSR — the recommended
|
|
16
|
+
* React idiom for a server/client-only value (avoids the extra
|
|
17
|
+
* render-then-setState pass a `useState`+`useEffect` mount flag causes). */
|
|
18
|
+
function useHasMounted() {
|
|
19
|
+
return React.useSyncExternalStore(subscribeNever, () => true, () => false);
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Recharts' `ResponsiveContainer` measures real DOM layout and produces no
|
|
23
|
+
* meaningful output during server-side `renderToString` — so this renders a
|
|
24
|
+
* fixed-height `Skeleton` until the client takes over, then swaps to the
|
|
25
|
+
* real chart. Server render and the client's initial (pre-hydration-settle)
|
|
26
|
+
* render both produce the same skeleton markup — no hydration mismatch.
|
|
27
|
+
*/
|
|
28
|
+
function ChartContainer(props) {
|
|
29
|
+
const mounted = useHasMounted();
|
|
30
|
+
if (!mounted) {
|
|
31
|
+
return _jsx(Skeleton, { className: "w-full rounded-md", style: { height: props.height } });
|
|
32
|
+
}
|
|
33
|
+
return (_jsx(ResponsiveContainer, { width: "100%", height: props.height, children: props.children }));
|
|
34
|
+
}
|
|
35
|
+
function ChartTooltipContent({ active, payload, label, }) {
|
|
36
|
+
if (!active || !payload?.length) {
|
|
37
|
+
return null;
|
|
38
|
+
}
|
|
39
|
+
return (_jsxs("div", { className: "rounded-md border border-border bg-card p-2 text-sm shadow-md", children: [label != null ? _jsx("div", { className: "mb-1 font-medium", children: label }) : null, payload.map((entry, index) => (_jsxs("div", { className: "flex items-center gap-1.5", children: [_jsx("span", { className: "inline-block size-2 rounded-full", style: { backgroundColor: entry.color } }), _jsxs("span", { className: "text-muted-foreground", children: [entry.name, ":"] }), _jsx("span", { className: "font-medium", children: entry.value })] }, index)))] }));
|
|
40
|
+
}
|
|
41
|
+
const legendStyle = { fontSize: 12, color: 'var(--muted-foreground)' };
|
|
42
|
+
function RechartsBar(props) {
|
|
43
|
+
return (_jsxs(RBarChart, { data: props.data, children: [_jsx(CartesianGrid, { strokeDasharray: "3 3", stroke: "var(--border)" }), _jsx(XAxis, { dataKey: props.categoryKey, stroke: "var(--muted-foreground)", fontSize: 12 }), _jsx(YAxis, { stroke: "var(--muted-foreground)", fontSize: 12, allowDecimals: false }), _jsx(Tooltip, { content: _jsx(ChartTooltipContent, {}) }), props.legend ? _jsx(Legend, { wrapperStyle: legendStyle }) : null, props.series.map((series, index) => (_jsx(Bar, { dataKey: series.key, name: series.label ?? series.key, fill: seriesColor(series, index), radius: [4, 4, 0, 0] }, series.key)))] }));
|
|
44
|
+
}
|
|
45
|
+
function RechartsLine(props) {
|
|
46
|
+
return (_jsxs(RLineChart, { data: props.data, children: [_jsx(CartesianGrid, { strokeDasharray: "3 3", stroke: "var(--border)" }), _jsx(XAxis, { dataKey: props.categoryKey, stroke: "var(--muted-foreground)", fontSize: 12 }), _jsx(YAxis, { stroke: "var(--muted-foreground)", fontSize: 12, allowDecimals: false }), _jsx(Tooltip, { content: _jsx(ChartTooltipContent, {}) }), props.legend ? _jsx(Legend, { wrapperStyle: legendStyle }) : null, props.series.map((series, index) => (_jsx(Line, { type: "monotone", dataKey: series.key, name: series.label ?? series.key, stroke: seriesColor(series, index), strokeWidth: 2, dot: false }, series.key)))] }));
|
|
47
|
+
}
|
|
48
|
+
function RechartsPie(props) {
|
|
49
|
+
const valueKey = props.series[0]?.key ?? 'value';
|
|
50
|
+
// `Cell` is deprecated in recharts 3.x — a per-slice `fill` set directly
|
|
51
|
+
// on each datum is the documented replacement for coloring a `Pie`.
|
|
52
|
+
const coloredData = props.data.map((row, index) => ({
|
|
53
|
+
...row,
|
|
54
|
+
fill: chartColorVar(((index % 5) + 1)),
|
|
55
|
+
}));
|
|
56
|
+
return (_jsxs(RPieChart, { children: [_jsx(Tooltip, { content: _jsx(ChartTooltipContent, {}) }), props.legend ? _jsx(Legend, { wrapperStyle: legendStyle }) : null, _jsx(Pie, { data: coloredData, dataKey: valueKey, nameKey: props.categoryKey, label: true })] }));
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Renders a `ChartSpec` (produced by `@nestjs-dash/core`'s `BarChart`/
|
|
60
|
+
* `LineChart`/`PieChart` builders) as a real, hydrated, interactive Recharts
|
|
61
|
+
* component — colored via the design system's existing `--chart-1..5`
|
|
62
|
+
* theme tokens.
|
|
63
|
+
*/
|
|
64
|
+
export function ChartWidget({ spec }) {
|
|
65
|
+
const legend = spec.legend ?? spec.kind === 'pie';
|
|
66
|
+
return (_jsxs(Card, { children: [spec.title || spec.description ? (_jsxs(CardHeader, { children: [spec.title ? _jsx(CardTitle, { children: spec.title }) : null, spec.description ? _jsx(CardDescription, { children: spec.description }) : null] })) : null, _jsx(CardContent, { children: spec.data.length === 0 ? (_jsx(EmptyState, { title: spec.emptyLabel ?? 'No data yet', description: spec.emptyLabel ? undefined : 'Nothing to chart yet.' })) : (_jsx(ChartContainer, { height: spec.height ?? 240, children: spec.kind === 'bar' ? (_jsx(RechartsBar, { data: spec.data, categoryKey: spec.categoryKey, series: spec.series, legend: legend })) : spec.kind === 'line' ? (_jsx(RechartsLine, { data: spec.data, categoryKey: spec.categoryKey, series: spec.series, legend: legend })) : (_jsx(RechartsPie, { data: spec.data, categoryKey: spec.categoryKey, series: spec.series, legend: legend })) })) })] }));
|
|
67
|
+
}
|
|
68
|
+
//# sourceMappingURL=chart.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chart.js","sourceRoot":"","sources":["../../src/components/chart.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { VariantProps } from 'class-variance-authority';
|
|
2
|
+
import type { ReactNode } from 'react';
|
|
3
|
+
import { buttonVariants } from './ui/button.js';
|
|
4
|
+
export declare function ConfirmDialog(props: {
|
|
5
|
+
trigger: ReactNode;
|
|
6
|
+
title: string;
|
|
7
|
+
description?: string;
|
|
8
|
+
confirmLabel?: string;
|
|
9
|
+
cancelLabel?: string;
|
|
10
|
+
/** Confirm button style. Defaults to 'destructive' (the common delete-confirmation case). */
|
|
11
|
+
confirmVariant?: VariantProps<typeof buttonVariants>['variant'];
|
|
12
|
+
formAction?: string;
|
|
13
|
+
method?: 'post' | 'get';
|
|
14
|
+
children?: ReactNode;
|
|
15
|
+
onConfirm?: () => void;
|
|
16
|
+
}): import("react").JSX.Element;
|
|
17
|
+
//# sourceMappingURL=confirm-dialog.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"confirm-dialog.d.ts","sourceRoot":"","sources":["../../src/components/confirm-dialog.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAC;AAC7D,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AACvC,OAAO,EAAU,cAAc,EAAE,MAAM,gBAAgB,CAAC;AAYxD,wBAAgB,aAAa,CAAC,KAAK,EAAE;IACnC,OAAO,EAAE,SAAS,CAAC;IACnB,KAAK,EAAE,MAAM,CAAC;IACd,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,6FAA6F;IAC7F,cAAc,CAAC,EAAE,YAAY,CAAC,OAAO,cAAc,CAAC,CAAC,SAAS,CAAC,CAAC;IAChE,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,MAAM,CAAC,EAAE,MAAM,GAAG,KAAK,CAAC;IACxB,QAAQ,CAAC,EAAE,SAAS,CAAC;IACrB,SAAS,CAAC,EAAE,MAAM,IAAI,CAAC;CACxB,+BA0CA"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
+
import { Button, buttonVariants } from './ui/button.js';
|
|
3
|
+
import { Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogTitle, DialogTrigger, } from './ui/dialog.js';
|
|
4
|
+
export function ConfirmDialog(props) {
|
|
5
|
+
const confirmVariant = props.confirmVariant ?? 'destructive';
|
|
6
|
+
return (_jsxs(Dialog, { children: [_jsx(DialogTrigger, { asChild: true, children: props.trigger }), _jsxs(DialogContent, { children: [_jsxs(DialogHeader, { children: [_jsx(DialogTitle, { children: props.title }), props.description ? _jsx(DialogDescription, { children: props.description }) : null] }), props.formAction ? (_jsxs("form", { method: props.method ?? 'post', action: props.formAction, className: "space-y-4", children: [props.children, _jsxs(DialogFooter, { children: [_jsx(DialogClose, { asChild: true, children: _jsx(Button, { type: "button", variant: "secondary", children: props.cancelLabel ?? 'Cancel' }) }), _jsx(Button, { type: "submit", variant: confirmVariant, children: props.confirmLabel ?? 'Confirm' })] })] })) : (_jsxs(_Fragment, { children: [props.children, _jsxs(DialogFooter, { children: [_jsx(DialogClose, { asChild: true, children: _jsx(Button, { type: "button", variant: "secondary", children: props.cancelLabel ?? 'Cancel' }) }), _jsx(Button, { type: "button", variant: confirmVariant, onClick: props.onConfirm, children: props.confirmLabel ?? 'Confirm' })] })] }))] })] }));
|
|
7
|
+
}
|
|
8
|
+
//# sourceMappingURL=confirm-dialog.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"confirm-dialog.js","sourceRoot":"","sources":["../../src/components/confirm-dialog.tsx"],"names":[],"mappings":";AAEA,OAAO,EAAE,MAAM,EAAE,cAAc,EAAE,MAAM,gBAAgB,CAAC;AACxD,OAAO,EACL,MAAM,EACN,WAAW,EACX,aAAa,EACb,iBAAiB,EACjB,YAAY,EACZ,YAAY,EACZ,WAAW,EACX,aAAa,GACd,MAAM,gBAAgB,CAAC;AAExB,MAAM,UAAU,aAAa,CAAC,KAY7B;IACC,MAAM,cAAc,GAAG,KAAK,CAAC,cAAc,IAAI,aAAa,CAAC;IAC7D,OAAO,CACL,MAAC,MAAM,eACL,KAAC,aAAa,IAAC,OAAO,kBAAE,KAAK,CAAC,OAAO,GAAiB,EACtD,MAAC,aAAa,eACZ,MAAC,YAAY,eACX,KAAC,WAAW,cAAE,KAAK,CAAC,KAAK,GAAe,EACvC,KAAK,CAAC,WAAW,CAAC,CAAC,CAAC,KAAC,iBAAiB,cAAE,KAAK,CAAC,WAAW,GAAqB,CAAC,CAAC,CAAC,IAAI,IACzE,EACd,KAAK,CAAC,UAAU,CAAC,CAAC,CAAC,CAClB,gBAAM,MAAM,EAAE,KAAK,CAAC,MAAM,IAAI,MAAM,EAAE,MAAM,EAAE,KAAK,CAAC,UAAU,EAAE,SAAS,EAAC,WAAW,aAClF,KAAK,CAAC,QAAQ,EACf,MAAC,YAAY,eACX,KAAC,WAAW,IAAC,OAAO,kBAClB,KAAC,MAAM,IAAC,IAAI,EAAC,QAAQ,EAAC,OAAO,EAAC,WAAW,YACtC,KAAK,CAAC,WAAW,IAAI,QAAQ,GACvB,GACG,EACd,KAAC,MAAM,IAAC,IAAI,EAAC,QAAQ,EAAC,OAAO,EAAE,cAAc,YAC1C,KAAK,CAAC,YAAY,IAAI,SAAS,GACzB,IACI,IACV,CACR,CAAC,CAAC,CAAC,CACF,8BACG,KAAK,CAAC,QAAQ,EACf,MAAC,YAAY,eACX,KAAC,WAAW,IAAC,OAAO,kBAClB,KAAC,MAAM,IAAC,IAAI,EAAC,QAAQ,EAAC,OAAO,EAAC,WAAW,YACtC,KAAK,CAAC,WAAW,IAAI,QAAQ,GACvB,GACG,EACd,KAAC,MAAM,IAAC,IAAI,EAAC,QAAQ,EAAC,OAAO,EAAE,cAAc,EAAE,OAAO,EAAE,KAAK,CAAC,SAAS,YACpE,KAAK,CAAC,YAAY,IAAI,SAAS,GACzB,IACI,IACd,CACJ,IACa,IACT,CACV,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
export interface PaginationMeta {
|
|
2
|
+
totalItems: number;
|
|
3
|
+
currentPage: number;
|
|
4
|
+
totalPages: number;
|
|
5
|
+
itemsPerPage?: number;
|
|
6
|
+
}
|
|
7
|
+
export declare function DataPagination(props: {
|
|
8
|
+
meta: PaginationMeta;
|
|
9
|
+
buildHref?: (page: number, limit: number) => string;
|
|
10
|
+
onPageChange?: (page: number) => void;
|
|
11
|
+
onLimitChange?: (limit: number) => void;
|
|
12
|
+
}): import("react").JSX.Element;
|
|
13
|
+
//# sourceMappingURL=data-pagination.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"data-pagination.d.ts","sourceRoot":"","sources":["../../src/components/data-pagination.tsx"],"names":[],"mappings":"AAaA,MAAM,WAAW,cAAc;IAC7B,UAAU,EAAE,MAAM,CAAC;IACnB,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC;IACnB,YAAY,CAAC,EAAE,MAAM,CAAC;CACvB;AAED,wBAAgB,cAAc,CAAC,KAAK,EAAE;IACpC,IAAI,EAAE,cAAc,CAAC;IACrB,SAAS,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,KAAK,MAAM,CAAC;IACpD,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;IACtC,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;CACzC,+BAuIA"}
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { buildPageWindow, pageSizeOptionsFor } from '../pagination.js';
|
|
3
|
+
import { Button } from './ui/button.js';
|
|
4
|
+
import { Pagination, PaginationContent, PaginationEllipsis, PaginationItem, PaginationLink, PaginationNext, PaginationPrevious, } from './ui/pagination.js';
|
|
5
|
+
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from './ui/select.js';
|
|
6
|
+
export function DataPagination(props) {
|
|
7
|
+
const currentPage = Math.max(props.meta.currentPage || 1, 1);
|
|
8
|
+
const totalPages = Math.max(props.meta.totalPages || 1, 1);
|
|
9
|
+
const itemsPerPage = props.meta.itemsPerPage != null && props.meta.itemsPerPage > 0
|
|
10
|
+
? Math.trunc(props.meta.itemsPerPage)
|
|
11
|
+
: 20;
|
|
12
|
+
const totalItems = props.meta.totalItems ?? 0;
|
|
13
|
+
const prevDisabled = currentPage <= 1;
|
|
14
|
+
const nextDisabled = currentPage >= totalPages;
|
|
15
|
+
const goToPage = (page) => {
|
|
16
|
+
if (props.onPageChange) {
|
|
17
|
+
props.onPageChange(page);
|
|
18
|
+
return;
|
|
19
|
+
}
|
|
20
|
+
if (props.buildHref && typeof window !== 'undefined') {
|
|
21
|
+
window.location.assign(props.buildHref(page, itemsPerPage));
|
|
22
|
+
}
|
|
23
|
+
};
|
|
24
|
+
const changeLimit = (limit) => {
|
|
25
|
+
if (props.onLimitChange) {
|
|
26
|
+
props.onLimitChange(limit);
|
|
27
|
+
return;
|
|
28
|
+
}
|
|
29
|
+
if (props.buildHref && typeof window !== 'undefined') {
|
|
30
|
+
window.location.assign(props.buildHref(1, limit));
|
|
31
|
+
}
|
|
32
|
+
};
|
|
33
|
+
const pageHref = (page) => props.buildHref && !props.onPageChange ? props.buildHref(page, itemsPerPage) : '#';
|
|
34
|
+
return (_jsxs("div", { className: "mt-4 flex flex-wrap items-center justify-between gap-3 border-t border-border pt-3", "data-afi-pagination": true, children: [_jsx("p", { className: "m-0 text-sm text-muted-foreground", children: `Page ${currentPage} of ${totalPages} · ${totalItems} items` }), _jsxs("div", { className: "flex flex-wrap items-center gap-2", children: [_jsxs("div", { className: "flex items-center gap-2 text-sm text-muted-foreground", children: [_jsx("span", { children: "Show" }), _jsxs(Select, { value: String(itemsPerPage), onValueChange: (value) => changeLimit(Number(value)), children: [_jsx(SelectTrigger, { size: "sm", className: "min-w-16", "aria-label": "Page size", children: _jsx(SelectValue, {}) }), _jsx(SelectContent, { children: pageSizeOptionsFor(itemsPerPage).map((size) => (_jsx(SelectItem, { value: String(size), children: size }, size))) })] })] }), _jsx(Pagination, { className: "mx-0 w-auto justify-start", children: _jsxs(PaginationContent, { children: [_jsx(PaginationItem, { children: prevDisabled ? (_jsx(Button, { variant: "ghost", size: "default", disabled: true, children: "Previous" })) : (_jsx(PaginationPrevious, { href: pageHref(currentPage - 1), onClick: (event) => {
|
|
35
|
+
if (props.onPageChange || !props.buildHref) {
|
|
36
|
+
event.preventDefault();
|
|
37
|
+
goToPage(currentPage - 1);
|
|
38
|
+
}
|
|
39
|
+
} })) }), buildPageWindow(currentPage, totalPages).map((item, index) => {
|
|
40
|
+
if (item === 'ellipsis') {
|
|
41
|
+
return (_jsx(PaginationItem, { children: _jsx(PaginationEllipsis, {}) }, `ellipsis-${index}`));
|
|
42
|
+
}
|
|
43
|
+
const isCurrent = item === currentPage;
|
|
44
|
+
return (_jsx(PaginationItem, { children: _jsx(PaginationLink, { href: pageHref(item), isActive: isCurrent, onClick: (event) => {
|
|
45
|
+
if (isCurrent) {
|
|
46
|
+
event.preventDefault();
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
if (props.onPageChange || !props.buildHref) {
|
|
50
|
+
event.preventDefault();
|
|
51
|
+
goToPage(item);
|
|
52
|
+
}
|
|
53
|
+
}, children: item }) }, item));
|
|
54
|
+
}), _jsx(PaginationItem, { children: nextDisabled ? (_jsx(Button, { variant: "ghost", size: "default", disabled: true, children: "Next" })) : (_jsx(PaginationNext, { href: pageHref(currentPage + 1), onClick: (event) => {
|
|
55
|
+
if (props.onPageChange || !props.buildHref) {
|
|
56
|
+
event.preventDefault();
|
|
57
|
+
goToPage(currentPage + 1);
|
|
58
|
+
}
|
|
59
|
+
} })) })] }) })] })] }));
|
|
60
|
+
}
|
|
61
|
+
//# sourceMappingURL=data-pagination.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"data-pagination.js","sourceRoot":"","sources":["../../src/components/data-pagination.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import type { SchemaNode } from '@nestjs-dash/support';
|
|
2
|
+
import type { ReactNode } from 'react';
|
|
3
|
+
import type { PaginationMeta } from './data-pagination.js';
|
|
4
|
+
export type SortDirection = 'ASC' | 'DESC';
|
|
5
|
+
export type SortBy = Array<[column: string, direction: SortDirection]>;
|
|
6
|
+
export declare function DataTable(props: {
|
|
7
|
+
columns: SchemaNode[];
|
|
8
|
+
rows: Array<Record<string, unknown>>;
|
|
9
|
+
meta?: PaginationMeta;
|
|
10
|
+
buildHref?: (page: number, limit: number) => string;
|
|
11
|
+
onPageChange?: (page: number) => void;
|
|
12
|
+
onLimitChange?: (limit: number) => void;
|
|
13
|
+
/** Override cell content per column; falls back to the built-in icon/text rendering. */
|
|
14
|
+
renderCell?: (column: SchemaNode, row: Record<string, unknown>) => ReactNode;
|
|
15
|
+
/** When provided, adds a trailing actions column rendered per row. */
|
|
16
|
+
renderRowActions?: (row: Record<string, unknown>) => ReactNode;
|
|
17
|
+
actionsLabel?: string;
|
|
18
|
+
emptyTitle?: string;
|
|
19
|
+
emptyDescription?: string;
|
|
20
|
+
/** Currently active sort, e.g. `[['name', 'ASC']]`. Only affects columns built with `.sortable()`. */
|
|
21
|
+
sortBy?: SortBy;
|
|
22
|
+
/** Build the URL to navigate to when a sortable column header is clicked. */
|
|
23
|
+
buildSortHref?: (column: string, direction: SortDirection) => string;
|
|
24
|
+
/** Handle sort clicks without a page navigation (client-only tables). */
|
|
25
|
+
onSortChange?: (column: string, direction: SortDirection) => void;
|
|
26
|
+
}): import("react").JSX.Element;
|
|
27
|
+
//# sourceMappingURL=data-table.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"data-table.d.ts","sourceRoot":"","sources":["../../src/components/data-table.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAc,UAAU,EAAE,MAAM,sBAAsB,CAAC;AACnE,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AAGvC,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAsC3D,MAAM,MAAM,aAAa,GAAG,KAAK,GAAG,MAAM,CAAC;AAC3C,MAAM,MAAM,MAAM,GAAG,KAAK,CAAC,CAAC,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,aAAa,CAAC,CAAC,CAAC;AAOvE,wBAAgB,SAAS,CAAC,KAAK,EAAE;IAC/B,OAAO,EAAE,UAAU,EAAE,CAAC;IACtB,IAAI,EAAE,KAAK,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;IACrC,IAAI,CAAC,EAAE,cAAc,CAAC;IACtB,SAAS,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,KAAK,MAAM,CAAC;IACpD,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;IACtC,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACxC,wFAAwF;IACxF,UAAU,CAAC,EAAE,CAAC,MAAM,EAAE,UAAU,EAAE,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,SAAS,CAAC;IAC7E,sEAAsE;IACtE,gBAAgB,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,SAAS,CAAC;IAC/D,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,sGAAsG;IACtG,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,6EAA6E;IAC7E,aAAa,CAAC,EAAE,CAAC,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,aAAa,KAAK,MAAM,CAAC;IACrE,yEAAyE;IACzE,YAAY,CAAC,EAAE,CAAC,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,aAAa,KAAK,IAAI,CAAC;CACnE,+BA6GA"}
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { BADGE_COLOR_CLASSES } from '../lib/badge-colors.js';
|
|
3
|
+
import { formatDate, formatRelativeTime, parseDateValue } from '../lib/format-date.js';
|
|
4
|
+
import { DataPagination } from './data-pagination.js';
|
|
5
|
+
import { EmptyState } from './empty-state.js';
|
|
6
|
+
import { Icon } from './icon.js';
|
|
7
|
+
import { Badge } from './ui/badge.js';
|
|
8
|
+
import { Button } from './ui/button.js';
|
|
9
|
+
import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from './ui/table.js';
|
|
10
|
+
function defaultCell(column, raw) {
|
|
11
|
+
switch (column.kind) {
|
|
12
|
+
case 'icon-column':
|
|
13
|
+
return raw ? _jsx(Icon, { name: String(raw) }) : null;
|
|
14
|
+
case 'badge-column': {
|
|
15
|
+
if (raw == null || raw === '')
|
|
16
|
+
return null;
|
|
17
|
+
const colors = (column.props.colors ?? {});
|
|
18
|
+
const color = colors[String(raw)];
|
|
19
|
+
return (_jsx(Badge, { variant: "outline", className: color ? BADGE_COLOR_CLASSES[color] : undefined, children: String(raw) }));
|
|
20
|
+
}
|
|
21
|
+
case 'boolean-column':
|
|
22
|
+
return raw ? (_jsx(Icon, { name: "circle-check", className: "text-green-600 dark:text-green-400" })) : (_jsx(Icon, { name: "circle-x", className: "text-red-600 dark:text-red-400" }));
|
|
23
|
+
case 'date-column': {
|
|
24
|
+
const date = parseDateValue(raw);
|
|
25
|
+
if (!date)
|
|
26
|
+
return null;
|
|
27
|
+
return column.props.since ? formatRelativeTime(date) : formatDate(date);
|
|
28
|
+
}
|
|
29
|
+
default:
|
|
30
|
+
return String(raw ?? '');
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
function sortDirectionFor(name, sortBy) {
|
|
34
|
+
const entry = sortBy?.find(([column]) => column === name);
|
|
35
|
+
return entry ? entry[1] : null;
|
|
36
|
+
}
|
|
37
|
+
export function DataTable(props) {
|
|
38
|
+
const sortInteractive = Boolean(props.buildSortHref || props.onSortChange);
|
|
39
|
+
function handleSortClick(column, direction) {
|
|
40
|
+
if (props.onSortChange) {
|
|
41
|
+
props.onSortChange(column, direction);
|
|
42
|
+
return;
|
|
43
|
+
}
|
|
44
|
+
if (props.buildSortHref && typeof window !== 'undefined') {
|
|
45
|
+
window.location.assign(props.buildSortHref(column, direction));
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
const table = props.rows.length === 0 ? (_jsx(EmptyState, { title: props.emptyTitle ?? 'No records', description: props.emptyDescription ?? 'Create a record to get started.' })) : (_jsxs(Table, { children: [_jsx(TableHeader, { children: _jsxs(TableRow, { children: [props.columns.map((column) => {
|
|
49
|
+
const name = String(column.name ?? '');
|
|
50
|
+
const label = String(column.props.label ?? column.name ?? '');
|
|
51
|
+
if (!sortInteractive || column.props.sortable !== true) {
|
|
52
|
+
return _jsx(TableHead, { children: label }, name);
|
|
53
|
+
}
|
|
54
|
+
const current = sortDirectionFor(name, props.sortBy);
|
|
55
|
+
const next = current === 'ASC' ? 'DESC' : 'ASC';
|
|
56
|
+
const href = props.buildSortHref?.(name, next);
|
|
57
|
+
return (_jsx(TableHead, { "aria-sort": current === 'ASC' ? 'ascending' : current === 'DESC' ? 'descending' : 'none', children: _jsx(Button, { asChild: true, variant: "ghost", size: "sm", className: "-ml-3 h-8 has-[>svg]:px-2", children: _jsxs("a", { href: href ?? '#', "data-afi-sort": name, "data-afi-sort-active": current != null, onClick: (event) => {
|
|
58
|
+
// Real href present (SSR link mode): let it navigate natively
|
|
59
|
+
// so sorting still works without JS. Only intercept for the
|
|
60
|
+
// client-callback mode.
|
|
61
|
+
if (props.onSortChange) {
|
|
62
|
+
event.preventDefault();
|
|
63
|
+
handleSortClick(name, next);
|
|
64
|
+
}
|
|
65
|
+
}, children: [label, _jsx(Icon, { name: current === 'ASC'
|
|
66
|
+
? 'arrow-up'
|
|
67
|
+
: current === 'DESC'
|
|
68
|
+
? 'arrow-down'
|
|
69
|
+
: 'chevrons-up-down', className: current ? 'text-foreground' : 'text-muted-foreground/60' })] }) }) }, name));
|
|
70
|
+
}), props.renderRowActions ? (_jsx(TableHead, { children: props.actionsLabel ?? 'Actions' })) : null] }) }), _jsx(TableBody, { children: props.rows.map((row, index) => (_jsxs(TableRow, { children: [props.columns.map((column) => {
|
|
71
|
+
if (props.renderCell) {
|
|
72
|
+
return (_jsx(TableCell, { children: props.renderCell(column, row) }, String(column.name)));
|
|
73
|
+
}
|
|
74
|
+
const raw = row[String(column.name)];
|
|
75
|
+
return _jsx(TableCell, { children: defaultCell(column, raw) }, String(column.name));
|
|
76
|
+
}), props.renderRowActions ? _jsx(TableCell, { children: props.renderRowActions(row) }) : null] }, String(row.id ?? index)))) })] }));
|
|
77
|
+
if (!props.meta) {
|
|
78
|
+
return table;
|
|
79
|
+
}
|
|
80
|
+
return (_jsxs("div", { children: [table, _jsx(DataPagination, { meta: props.meta, buildHref: props.buildHref, onPageChange: props.onPageChange, onLimitChange: props.onLimitChange })] }));
|
|
81
|
+
}
|
|
82
|
+
//# sourceMappingURL=data-table.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"data-table.js","sourceRoot":"","sources":["../../src/components/data-table.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"empty-state.d.ts","sourceRoot":"","sources":["../../src/components/empty-state.tsx"],"names":[],"mappings":"AAAA,wBAAgB,UAAU,CAAC,KAAK,EAAE;IAAE,KAAK,EAAE,MAAM,CAAC;IAAC,WAAW,CAAC,EAAE,MAAM,CAAA;CAAE,+BASxE"}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
export function EmptyState(props) {
|
|
3
|
+
return (_jsxs("div", { className: "p-8 text-center text-muted-foreground", "data-slot": "empty-state", children: [_jsx("h3", { className: "text-base font-semibold text-foreground", children: props.title }), props.description ? (_jsx("p", { className: "mt-1 text-sm text-muted-foreground", children: props.description })) : null] }));
|
|
4
|
+
}
|
|
5
|
+
//# sourceMappingURL=empty-state.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"empty-state.js","sourceRoot":"","sources":["../../src/components/empty-state.tsx"],"names":[],"mappings":";AAAA,MAAM,UAAU,UAAU,CAAC,KAA8C;IACvE,OAAO,CACL,eAAK,SAAS,EAAC,uCAAuC,eAAW,aAAa,aAC5E,aAAI,SAAS,EAAC,yCAAyC,YAAE,KAAK,CAAC,KAAK,GAAM,EACzE,KAAK,CAAC,WAAW,CAAC,CAAC,CAAC,CACnB,YAAG,SAAS,EAAC,oCAAoC,YAAE,KAAK,CAAC,WAAW,GAAK,CAC1E,CAAC,CAAC,CAAC,IAAI,IACJ,CACP,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
export type FileUploadItem = {
|
|
2
|
+
path?: string;
|
|
3
|
+
url?: string;
|
|
4
|
+
disk?: string;
|
|
5
|
+
fileName?: string;
|
|
6
|
+
mimeType?: string;
|
|
7
|
+
size?: number;
|
|
8
|
+
};
|
|
9
|
+
/**
|
|
10
|
+
* Interactive generic file field: file list, native picker, and a hidden JSON
|
|
11
|
+
* payload input so the surrounding `<form>` POST carries the uploaded items —
|
|
12
|
+
* same pattern as `ImageUploadField`, without the image preview/crop UI.
|
|
13
|
+
*/
|
|
14
|
+
export declare function FileUploadField(props: {
|
|
15
|
+
name: string;
|
|
16
|
+
label: string;
|
|
17
|
+
multiple?: boolean;
|
|
18
|
+
maxFiles?: number;
|
|
19
|
+
maxSizeKb?: number;
|
|
20
|
+
accept?: string;
|
|
21
|
+
disk?: string;
|
|
22
|
+
directory?: string;
|
|
23
|
+
visibility?: string;
|
|
24
|
+
required?: boolean;
|
|
25
|
+
defaultValue?: unknown;
|
|
26
|
+
uploadUrl: string;
|
|
27
|
+
}): import("react").JSX.Element;
|
|
28
|
+
//# sourceMappingURL=file-upload-field.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"file-upload-field.d.ts","sourceRoot":"","sources":["../../src/components/file-upload-field.tsx"],"names":[],"mappings":"AAMA,MAAM,MAAM,cAAc,GAAG;IAC3B,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf,CAAC;AA0BF;;;;GAIG;AACH,wBAAgB,eAAe,CAAC,KAAK,EAAE;IACrC,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,SAAS,EAAE,MAAM,CAAC;CACnB,+BA+GA"}
|