kmod-cli 1.0.10 → 1.1.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.
@@ -37,61 +37,61 @@ import {
37
37
  } from './table';
38
38
 
39
39
  export type TableHeaderClassNames = {
40
- header?: string;
41
- row?: string;
42
- head?: string;
40
+ header?: string;
41
+ row?: string;
42
+ head?: string;
43
43
  };
44
44
  export type TableBodyClassNames = {
45
- body?: string;
46
- row?: string;
47
- cell?: string;
45
+ body?: string;
46
+ row?: string;
47
+ cell?: string;
48
48
  };
49
49
  export type TableClassNames = {
50
- wrapper?: string;
51
- container?: string;
52
- table?: string;
53
- header?: TableHeaderClassNames;
54
- body?: TableBodyClassNames;
50
+ wrapper?: string;
51
+ container?: string;
52
+ table?: string;
53
+ header?: TableHeaderClassNames;
54
+ body?: TableBodyClassNames;
55
55
  };
56
56
  export type TableHeaderProps<TData> = HTMLAttributes<HTMLTableSectionElement> & {
57
- handleClick: ({ e, table }: { e: React.MouseEvent<HTMLTableSectionElement>; table: ITable<TData> }) => void;
58
-
57
+ handleClick: ({ e, table }: { e: React.MouseEvent<HTMLTableSectionElement>; table: ITable<TData> }) => void;
58
+
59
59
  };
60
60
  export type TableBodyProps<TData> = HTMLAttributes<HTMLTableSectionElement> & {
61
- handleClick: ({ e, table }: { e: React.MouseEvent<HTMLTableSectionElement>; table: ITable<TData> }) => void;
61
+ handleClick: ({ e, table }: { e: React.MouseEvent<HTMLTableSectionElement>; table: ITable<TData> }) => void;
62
62
  };
63
63
  export type TableHeadProps<TData> = HTMLAttributes<HTMLTableCellElement> & {
64
- handleClick: ({
65
- e,
66
- table,
67
- cell,
68
- }: {
69
- e: React.MouseEvent<HTMLTableCellElement>;
70
- cell: Header<TData, unknown>;
71
- table: ITable<TData>;
72
- }) => void;
64
+ handleClick: ({
65
+ e,
66
+ table,
67
+ cell,
68
+ }: {
69
+ e: React.MouseEvent<HTMLTableCellElement>;
70
+ cell: Header<TData, unknown>;
71
+ table: ITable<TData>;
72
+ }) => void;
73
73
  };
74
74
  export type TableCellProps<TData, TValue> = HTMLAttributes<HTMLTableCellElement> & {
75
- handleClick: ({ e, table, cell }: { e: React.MouseEvent<HTMLTableCellElement>; cell: Cell<TData, TValue>; table: ITable<TData> }) => void;
75
+ handleClick: ({ e, table, cell }: { e: React.MouseEvent<HTMLTableCellElement>; cell: Cell<TData, TValue>; table: ITable<TData> }) => void;
76
76
  };
77
77
  export type TableRowHeadProps<TData> = HTMLAttributes<HTMLTableRowElement> & {
78
- handleClick: ({ e, table, row }: { e: React.MouseEvent<HTMLTableRowElement>; row: HeaderGroup<TData>; table: ITable<TData> }) => void;
78
+ handleClick: ({ e, table, row }: { e: React.MouseEvent<HTMLTableRowElement>; row: HeaderGroup<TData>; table: ITable<TData> }) => void;
79
79
  };
80
80
  export type TableRowBodyProps<TData> = HTMLAttributes<HTMLTableRowElement> & {
81
- handleClick: ({ e, table, row }: { e: React.MouseEvent<HTMLTableRowElement>; row: Row<TData>; table: ITable<TData> }) => void;
81
+ handleClick: ({ e, table, row }: { e: React.MouseEvent<HTMLTableRowElement>; row: Row<TData>; table: ITable<TData> }) => void;
82
82
  };
83
83
  export type TableProps<TData> = HTMLAttributes<HTMLTableElement> & {
84
- handleClick: ({ e, table }: { e: React.MouseEvent<HTMLTableElement>; table: ITable<TData> }) => void;
84
+ handleClick: ({ e, table }: { e: React.MouseEvent<HTMLTableElement>; table: ITable<TData> }) => void;
85
85
  };
86
86
 
87
87
  export type UseTableProps<TData, TValue> = {
88
- tableProps?: TableProps<TData>;
89
- headerProps?: TableHeaderProps<TData>;
90
- bodyProps?: TableBodyProps<TData>;
91
- cellBodyProps?: TableCellProps<TData, TValue>;
92
- rowHeadProps?: TableRowHeadProps<TData>;
93
- rowBodyProps?: TableRowBodyProps<TData>;
94
- cellHeadProps?: TableHeadProps<TData>;
88
+ tableProps?: TableProps<TData>;
89
+ headerProps?: TableHeaderProps<TData>;
90
+ bodyProps?: TableBodyProps<TData>;
91
+ cellBodyProps?: TableCellProps<TData, TValue>;
92
+ rowHeadProps?: TableRowHeadProps<TData>;
93
+ rowBodyProps?: TableRowBodyProps<TData>;
94
+ cellHeadProps?: TableHeadProps<TData>;
95
95
  };
96
96
 
97
97
  // export type Handles = {
@@ -109,231 +109,240 @@ export type UseTableProps<TData, TValue> = {
109
109
  // }
110
110
 
111
111
  export type DataTableProps<TData, TValue> = {
112
- columns: ColumnDef<TData, TValue>[];
113
- data: TData[];
114
- toolbarTable?: ({ table, fns }: { table: ITable<TData>; fns: DataTableToolbarFns<TData> }) => ReactNode | ReactNode[];
115
- paginationTable?: ({ table, fns }: { table: ITable<TData>; fns: DataTablePaginationFns<TData> }) => ReactNode | ReactNode[];
116
- isLoading?: boolean;
117
- classNames?: TableClassNames;
118
- emptyLabel?: string;
119
- showSortIconHeader?: boolean;
120
- surfix?: ({
121
- header,
122
- showSortIconHeader,
123
- }: {
124
- header: Header<TData, TValue | unknown>;
125
- showSortIconHeader: boolean;
126
- }) => ReactNode | ReactNode[];
127
- enableSort?: boolean;
128
- useTableProps?: UseTableProps<TData, TValue>;
129
- initialState?: InitialTableState;
130
- // handles?: Handles
112
+ columns: ColumnDef<TData, TValue>[];
113
+ data: TData[];
114
+ toolbarTable?: ({ table, fns }: { table: ITable<TData>; fns: DataTableToolbarFns<TData> }) => ReactNode | ReactNode[];
115
+ paginationTable?: ({ table, fns }: { table: ITable<TData>; fns: DataTablePaginationFns<TData> }) => ReactNode | ReactNode[];
116
+ isLoading?: boolean;
117
+ classNames?: TableClassNames;
118
+ emptyLabel?: string;
119
+ showSortIconHeader?: boolean;
120
+ surfix?: ({
121
+ header,
122
+ showSortIconHeader,
123
+ }: {
124
+ header: Header<TData, TValue | unknown>;
125
+ showSortIconHeader: boolean;
126
+ }) => ReactNode | ReactNode[];
127
+ enableSort?: boolean;
128
+ useTableProps?: UseTableProps<TData, TValue>;
129
+ initialState?: InitialTableState;
130
+ // handles?: Handles
131
131
  };
132
132
 
133
133
  export type DataTableToolbarFns<TData> = {
134
- globalFilter: string;
135
- setGlobalFilter: (value: string) => void;
136
- sorting: any;
137
- setSorting: (value: any) => void;
138
- getColumn: (columnId: string) => ReturnType<ITable<TData>["getColumn"]>;
134
+ globalFilter: string;
135
+ setGlobalFilter: (value: string) => void;
136
+ sorting: any;
137
+ setSorting: (value: any) => void;
138
+ getColumn: (columnId: string) => ReturnType<ITable<TData>["getColumn"]>;
139
139
  };
140
140
 
141
141
  export type DataTablePaginationFns<TData> = {
142
- previousPage: () => void;
143
- nextPage: () => void;
144
- getCanPreviousPage: () => boolean;
145
- getCanNextPage: () => boolean;
146
- pageIndex: number;
147
- pageSize: number;
142
+ previousPage: () => void;
143
+ nextPage: () => void;
144
+ getCanPreviousPage: () => boolean;
145
+ getCanNextPage: () => boolean;
146
+ pageIndex: number;
147
+ pageSize: number;
148
148
  };
149
149
 
150
150
  export function DataTable<TData, TValue>({
151
- columns,
152
- data,
153
- toolbarTable,
154
- paginationTable,
155
- classNames,
156
- isLoading = false,
157
- emptyLabel = "No data",
158
- showSortIconHeader = true,
159
- surfix,
160
- enableSort = true,
161
- useTableProps,
162
- initialState,
163
- // handles
164
- }: DataTableProps<TData, TValue>) {
165
- const table = useReactTable({
166
- data,
167
- columns,
168
- getCoreRowModel: getCoreRowModel(),
169
- getFilteredRowModel: getFilteredRowModel(),
170
- getPaginationRowModel: getPaginationRowModel(),
171
- getSortedRowModel: enableSort ? getSortedRowModel() : undefined,
172
- initialState: initialState,
173
- });
174
- const toolbarFns: DataTableToolbarFns<TData> = {
175
- globalFilter: table.getState().globalFilter as string,
176
- setGlobalFilter: table.setGlobalFilter,
177
- sorting: table.getState().sorting,
178
- setSorting: table.setSorting,
179
- getColumn: table.getColumn,
180
- };
181
- const paginationFns: DataTablePaginationFns<TData> = {
182
- previousPage: table.previousPage,
183
- nextPage: table.nextPage,
184
- getCanPreviousPage: table.getCanPreviousPage,
185
- getCanNextPage: table.getCanNextPage,
186
- pageIndex: table.getState().pagination.pageIndex,
187
- pageSize: table.getState().pagination.pageSize,
188
- };
151
+ columns,
152
+ data,
153
+ toolbarTable,
154
+ paginationTable,
155
+ classNames,
156
+ isLoading = false,
157
+ emptyLabel = "No data",
158
+ showSortIconHeader = true,
159
+ surfix,
160
+ enableSort = true,
161
+ useTableProps,
162
+ initialState,
163
+ // handles
164
+ }: DataTableProps<TData, TValue>) {
165
+ const table = useReactTable({
166
+ data,
167
+ columns,
168
+ getCoreRowModel: getCoreRowModel(),
169
+ getFilteredRowModel: getFilteredRowModel(),
170
+ getPaginationRowModel: getPaginationRowModel(),
171
+ getSortedRowModel: enableSort ? getSortedRowModel() : undefined,
172
+ initialState: initialState,
173
+ });
174
+ const toolbarFns: DataTableToolbarFns<TData> = {
175
+ globalFilter: table.getState().globalFilter as string,
176
+ setGlobalFilter: table.setGlobalFilter,
177
+ sorting: table.getState().sorting,
178
+ setSorting: table.setSorting,
179
+ getColumn: table.getColumn,
180
+ };
181
+ const paginationFns: DataTablePaginationFns<TData> = {
182
+ previousPage: table.previousPage,
183
+ nextPage: table.nextPage,
184
+ getCanPreviousPage: table.getCanPreviousPage,
185
+ getCanNextPage: table.getCanNextPage,
186
+ pageIndex: table.getState().pagination.pageIndex,
187
+ pageSize: table.getState().pagination.pageSize,
188
+ };
189
189
 
190
- return (
191
- <div className={cn("space-y-4", classNames?.wrapper)}>
192
- {toolbarTable && toolbarTable({ table, fns: toolbarFns })}
193
- <div className={cn(classNames?.container)}>
194
- <Table
195
- className={cn(classNames?.table)}
196
- {...useTableProps?.tableProps}
197
- onClick={(e) => useTableProps?.tableProps?.handleClick({ e, table })}
198
- >
199
- <TableHeader
200
- className={cn(classNames?.header?.header)}
201
- {...useTableProps?.headerProps}
202
- onClick={(e) => useTableProps?.headerProps?.handleClick({ e, table })}
203
- >
204
- {table.getHeaderGroups().map((headerGroup) => (
205
- <TableRow
206
- key={headerGroup.id}
207
- className={cn(classNames?.header?.row)}
208
- {...useTableProps?.rowHeadProps}
209
- onClick={(e) => useTableProps?.rowHeadProps?.handleClick({ e, row: headerGroup, table })}
210
- >
211
- {headerGroup.headers.map((header) => (
212
- <TableHead
213
- key={header.id}
214
- className={cn("cursor-pointer select-none", classNames?.header?.head)}
215
- onClick={(e) => {
216
- header.column.getToggleSortingHandler();
190
+ return (
191
+ <div className={cn("space-y-4", classNames?.wrapper)}>
192
+ {toolbarTable && toolbarTable({ table, fns: toolbarFns })}
193
+ <div className={cn(classNames?.container)}>
194
+ <Table
195
+ className={cn(classNames?.table)}
196
+ {...useTableProps?.tableProps}
197
+ onClick={(e) => useTableProps?.tableProps?.handleClick({ e, table })}
198
+ >
199
+ <TableHeader
200
+ className={cn(classNames?.header?.header)}
201
+ {...useTableProps?.headerProps}
202
+ onClick={(e) => useTableProps?.headerProps?.handleClick({ e, table })}
203
+ >
204
+ {table.getHeaderGroups().map((headerGroup) => (
205
+ <TableRow
206
+ key={headerGroup.id}
207
+ className={cn(classNames?.header?.row)}
208
+ {...useTableProps?.rowHeadProps}
209
+ onClick={(e) => useTableProps?.rowHeadProps?.handleClick({ e, row: headerGroup, table })}
210
+ >
211
+ {headerGroup.headers.map((header) => (
212
+ <TableHead
213
+ key={header.id}
214
+ {...(() => {
215
+ const { handleClick, onClick, ...rest } = useTableProps?.cellHeadProps || {};
216
+ return rest;
217
+ })()}
218
+ className={cn("cursor-pointer select-none", classNames?.header?.head)}
219
+ onClick={(e) => {
220
+ // Just call the parent's onClick if provided
221
+ if (useTableProps?.cellHeadProps?.onClick) {
222
+ useTableProps.cellHeadProps.onClick(e);
223
+ }
217
224
 
218
- if (useTableProps?.headerProps?.handleClick) {
219
- useTableProps?.cellHeadProps?.handleClick({ e, cell: header, table });
220
- }
221
- }}
222
- {...useTableProps?.cellHeadProps}
223
- >
224
- {flexRender(header.column.columnDef.header, header.getContext())}
225
- {table.getRowModel().rows.length > 0 && surfix && surfix({ header, showSortIconHeader })}
226
- </TableHead>
227
- ))}
228
- </TableRow>
229
- ))}
230
- </TableHeader>
225
+ // Just call the parent's handleClick if provided
226
+ if (useTableProps?.cellHeadProps?.handleClick) {
227
+ useTableProps.cellHeadProps.handleClick({ e, cell: header, table });
228
+ }
229
+ }}
230
+ >
231
+ <div className="flex items-center gap-1">
232
+ {flexRender(header.column.columnDef.header, header.getContext())}
233
+ {table.getRowModel().rows.length > 0 && surfix && surfix({ header, showSortIconHeader })}
234
+ </div>
235
+ </TableHead>
236
+ ))}
237
+ </TableRow>
238
+ ))}
239
+ </TableHeader>
231
240
 
232
- <TableBody
233
- className={cn(classNames?.body?.body)}
234
- {...useTableProps?.bodyProps}
235
- onClick={(e) => useTableProps?.bodyProps?.handleClick({ e, table })}
236
- >
237
- {isLoading && (
238
- <TableSkeleton
239
- props={useTableProps}
240
- isLoading={isLoading}
241
- classNames={classNames}
242
- emptyLabel={emptyLabel}
243
- columns={columns}
244
- />
245
- )}
246
- {!isLoading &&
247
- table.getRowModel().rows.length > 0 &&
248
- table.getRowModel().rows.map((row) => (
249
- <TableRow
250
- key={row.id}
251
- className={cn(classNames?.body?.row)}
252
- data-state={row.getIsSelected() && "selected"}
253
- {...useTableProps?.rowBodyProps}
254
- onClick={(e) => useTableProps?.rowBodyProps?.handleClick({ e, row, table })}
255
- >
256
- {row.getVisibleCells().map((cell) => (
257
- <TableCell
258
- key={cell.id}
259
- className={cn(classNames?.body?.cell)}
260
- {...useTableProps?.cellBodyProps}
261
- onClick={(e) => useTableProps?.cellBodyProps?.handleClick({ e, cell, table })}
241
+ <TableBody
242
+ className={cn(classNames?.body?.body)}
243
+ {...useTableProps?.bodyProps}
244
+ onClick={(e) => useTableProps?.bodyProps?.handleClick({ e, table })}
262
245
  >
263
- {flexRender(cell.column.columnDef.cell, cell.getContext())}
264
- </TableCell>
265
- ))}
266
- </TableRow>
267
- ))}
268
- {!isLoading && table.getRowModel().rows.length === 0 && (
269
- <TableRow key="no-data" className={cn(classNames?.body?.row)} {...useTableProps?.rowBodyProps}>
270
- <TableCell
271
- colSpan={columns.length}
272
- className={cn("h-24 text-center", classNames?.body?.cell)}
273
- {...useTableProps?.cellBodyProps}
274
- >
275
- {emptyLabel}
276
- </TableCell>
277
- </TableRow>
278
- )}
279
- </TableBody>
280
- </Table>
281
- </div>
282
- {paginationTable && paginationTable({ table, fns: paginationFns })}
283
- </div>
284
- );
246
+ {isLoading && (
247
+ <TableSkeleton
248
+ props={useTableProps}
249
+ isLoading={isLoading}
250
+ classNames={classNames}
251
+ emptyLabel={emptyLabel}
252
+ columns={columns}
253
+ />
254
+ )}
255
+ {!isLoading &&
256
+ table.getRowModel().rows.length > 0 &&
257
+ table.getRowModel().rows.map((row) => (
258
+ <TableRow
259
+ key={row.id}
260
+ className={cn(classNames?.body?.row)}
261
+ data-state={row.getIsSelected() && "selected"}
262
+ {...useTableProps?.rowBodyProps}
263
+ onClick={(e) => useTableProps?.rowBodyProps?.handleClick({ e, row, table })}
264
+ >
265
+ {row.getVisibleCells().map((cell) => (
266
+ <TableCell
267
+ key={cell.id}
268
+ className={cn(classNames?.body?.cell)}
269
+ {...useTableProps?.cellBodyProps}
270
+ onClick={(e) => useTableProps?.cellBodyProps?.handleClick({ e, cell, table })}
271
+ >
272
+ {flexRender(cell.column.columnDef.cell, cell.getContext())}
273
+ </TableCell>
274
+ ))}
275
+ </TableRow>
276
+ ))}
277
+ {!isLoading && table.getRowModel().rows.length === 0 && (
278
+ <TableRow key="no-data" className={cn(classNames?.body?.row)} {...useTableProps?.rowBodyProps}>
279
+ <TableCell
280
+ colSpan={columns.length}
281
+ className={cn("h-24 text-center", classNames?.body?.cell)}
282
+ {...useTableProps?.cellBodyProps}
283
+ >
284
+ {emptyLabel}
285
+ </TableCell>
286
+ </TableRow>
287
+ )}
288
+ </TableBody>
289
+ </Table>
290
+ </div>
291
+ {paginationTable && paginationTable({ table, fns: paginationFns })}
292
+ </div>
293
+ );
285
294
  }
286
295
 
287
296
  type TableSkeletonProps<TData, TValue> = {
288
- isLoading: boolean;
289
- classNames?: TableClassNames;
290
- emptyLabel?: string;
291
- columns: ColumnDef<TData, TValue>[];
292
- props?: UseTableProps<TData, TValue>;
297
+ isLoading: boolean;
298
+ classNames?: TableClassNames;
299
+ emptyLabel?: string;
300
+ columns: ColumnDef<TData, TValue>[];
301
+ props?: UseTableProps<TData, TValue>;
293
302
  };
294
303
 
295
304
  export const TableSkeleton = <TData, TValue>({ isLoading, classNames, emptyLabel, props, columns }: TableSkeletonProps<TData, TValue>) => {
296
- const [showNoData, setShowNoData] = useState(false);
297
- const timerRef = useRef<NodeJS.Timeout | null>(null);
305
+ const [showNoData, setShowNoData] = useState(false);
306
+ const timerRef = useRef<NodeJS.Timeout | null>(null);
298
307
 
299
- useEffect(() => {
300
- if (isLoading) {
301
- timerRef.current = setTimeout(() => setShowNoData(true), 10000);
302
- } else {
303
- setShowNoData(false);
304
- if (timerRef.current) {
305
- clearTimeout(timerRef.current);
306
- timerRef.current = null;
307
- }
308
- }
309
- return () => {
310
- if (timerRef.current) {
311
- clearTimeout(timerRef.current);
312
- timerRef.current = null;
313
- }
314
- };
315
- }, [isLoading]);
308
+ useEffect(() => {
309
+ if (isLoading) {
310
+ timerRef.current = setTimeout(() => setShowNoData(true), 10000);
311
+ } else {
312
+ setShowNoData(false);
313
+ if (timerRef.current) {
314
+ clearTimeout(timerRef.current);
315
+ timerRef.current = null;
316
+ }
317
+ }
318
+ return () => {
319
+ if (timerRef.current) {
320
+ clearTimeout(timerRef.current);
321
+ timerRef.current = null;
322
+ }
323
+ };
324
+ }, [isLoading]);
316
325
 
317
- if (showNoData) {
326
+ if (showNoData) {
327
+ return (
328
+ <TableRow key="no-data-skeleton" className={cn(classNames?.body?.row)} {...props?.rowBodyProps}>
329
+ <TableCell colSpan={columns.length} className={cn("h-24 text-center", classNames?.body?.cell)} {...props?.cellBodyProps}>
330
+ {emptyLabel}
331
+ </TableCell>
332
+ </TableRow>
333
+ );
334
+ }
318
335
  return (
319
- <TableRow key="no-data-skeleton" className={cn(classNames?.body?.row)} {...props?.rowBodyProps}>
320
- <TableCell colSpan={columns.length} className={cn("h-24 text-center", classNames?.body?.cell)} {...props?.cellBodyProps}>
321
- {emptyLabel}
322
- </TableCell>
323
- </TableRow>
336
+ <>
337
+ {[...Array(5)].map((_, rowIndex) => (
338
+ <TableRow key={`skeleton-${rowIndex}`} className={cn(classNames?.body?.row)} {...props?.rowBodyProps}>
339
+ {columns.map((_, colIndex) => (
340
+ <TableCell key={`skeleton-${rowIndex}-${colIndex}`} className={cn(classNames?.body?.cell)} {...props?.cellBodyProps}>
341
+ <div className="shimmer h-4 w-full" />
342
+ </TableCell>
343
+ ))}
344
+ </TableRow>
345
+ ))}
346
+ </>
324
347
  );
325
- }
326
- return (
327
- <>
328
- {[...Array(5)].map((_, rowIndex) => (
329
- <TableRow key={`skeleton-${rowIndex}`} className={cn(classNames?.body?.row)} {...props?.rowBodyProps}>
330
- {columns.map((_, colIndex) => (
331
- <TableCell key={`skeleton-${rowIndex}-${colIndex}`} className={cn(classNames?.body?.cell)} {...props?.cellBodyProps}>
332
- <div className="shimmer h-4 w-full" />
333
- </TableCell>
334
- ))}
335
- </TableRow>
336
- ))}
337
- </>
338
- );
339
- };
348
+ };
@@ -0,0 +1,9 @@
1
+ import {
2
+ type ClassValue,
3
+ clsx,
4
+ } from 'clsx';
5
+ import { twMerge } from 'tailwind-merge';
6
+
7
+ export function cn(...inputs: ClassValue[]) {
8
+ return twMerge(clsx(inputs))
9
+ }