1
2import {
3 ColumnDef,
4 ColumnFiltersState,
5 SortingState,
6 VisibilityState,
7 flexRender,
8 getCoreRowModel,
9 getFilteredRowModel,
10 getPaginationRowModel,
11 getSortedRowModel,
12 useReactTable,
13} from "@tanstack/react-table"
14import {
15 Button,
16 Input,
17 DataTablePagination,
18 DataTableViewOptions,
19 Popover,
20 PopoverTrigger,
21 PopoverContent,
22 Table,
23 TableHeader,
24 TableRow,
25 TableHead,
26 TableCell,
27 TableBody,
28 ToggleGroup,
29 ToggleGroupItem,
30 ScrollArea
31} from "@marzneshin/components"
32import { useTranslation } from "react-i18next"
33import { useState } from "react"
34import { InboundType } from "@marzneshin/features/inbounds"
35import { Server } from "lucide-react"
36import { InboundOption } from "./inbound"
37
38interface InboundHostsDataTableProps<TData, TValue> {
39 columns: ColumnDef<TData, TValue>[]
40 data: TData[]
41 inbounds: InboundType[]
42 filteredColumn: string
43 selectedInbound: string | undefined
44 setSelectedInbound: (s: string) => void
45 onCreate?: () => void
46 onOpen?: (object: TData) => void
47}
48
49export function InboundHostsDataTable<TData, TValue>({
50 columns,
51 data,
52 onCreate,
53 onOpen,
54 filteredColumn,
55 inbounds,
56 selectedInbound,
57 setSelectedInbound,
58}: InboundHostsDataTableProps<TData, TValue>) {
59 const [sorting, setSorting] = useState<SortingState>([])
60 const [columnFilters, setColumnFilters] = useState<ColumnFiltersState>([])
61 const [columnVisibility, setColumnVisibility] = useState<VisibilityState>({})
62 const table = useReactTable({
63 data,
64 columns,
65 onSortingChange: setSorting,
66 onColumnFiltersChange: setColumnFilters,
67 getCoreRowModel: getCoreRowModel(),
68 getPaginationRowModel: getPaginationRowModel(),
69 getSortedRowModel: getSortedRowModel(),
70 getFilteredRowModel: getFilteredRowModel(),
71 onColumnVisibilityChange: setColumnVisibility,
72 state: {
73 sorting,
74 columnFilters,
75 columnVisibility,
76 },
77 })
78 const { t } = useTranslation();
79 return (
80 <div>
81 <div className="flex justify-between items-center py-4">
82 <Input
83 placeholder={t('table.filter-placeholder', { name: filteredColumn })}
84 value={(table.getColumn(filteredColumn)?.getFilterValue() as string) ?? ""}
85 onChange={(event) =>
86 table.getColumn(filteredColumn)?.setFilterValue(event.target.value)
87 }
88 className="max-w-sm"
89 />
90 <div className="flex items-center">
91 <Popover >
92 <PopoverTrigger asChild>
93 <Button
94 variant="outline"
95 className="mr-2 ml-auto lg:flex"
96 >
97 <Server className="mr-2 w-4 h-4" />
98 {t('inbounds')}
99 </Button>
100 </PopoverTrigger>
101 <PopoverContent className="w-80 max-h-100">
102 <ToggleGroup type="single" onValueChange={setSelectedInbound} defaultValue={selectedInbound} className="flex flex-col justify-center w-full h-full" >
103 <ScrollArea className="w-full h-full">
104 {inbounds.map((inbound) => {
105 return <ToggleGroupItem className="px-0 w-full h-full" value={String(inbound.id)} id={String(inbound.id)}>
106 <InboundOption inbound={inbound} />
107 </ToggleGroupItem>
108 })}
109 </ScrollArea>
110 </ToggleGroup>
111 </PopoverContent>
112 </Popover>
113 <DataTableViewOptions table={table} />
114 {onCreate && (<Button onClick={onCreate}>{t('create')}</Button>)}
115 </div>
116 </div>
117 <div className="rounded-md border">
118 <div>
119 <Table>
120 <TableHeader>
121 {table.getHeaderGroups().map((headerGroup) => (
122 <TableRow key={headerGroup.id}>
123 {headerGroup.headers.map((header) => {
124 return (
125 <TableHead key={header.id}>
126 {header.isPlaceholder
127 ? null
128 : flexRender(
129 header.column.columnDef.header,
130 header.getContext()
131 )}
132 </TableHead>
133 )
134 })}
135 </TableRow>
136 ))}
137 </TableHeader>
138 <TableBody>
139 {table.getRowModel().rows?.length ? (
140 table.getRowModel().rows.map((row) => (
141 <TableRow
142 key={row.id}
143 data-state={row.getIsSelected() && "selected"}
144 onClick={() => onOpen !== undefined && onOpen(row.original)}
145 >
146 {row.getVisibleCells().map((cell) => (
147 <TableCell key={cell.id}>
148 {flexRender(cell.column.columnDef.cell, cell.getContext())}
149 </TableCell>
150 ))}
151 </TableRow>
152 ))
153 ) : (
154 <TableRow>
155 <TableCell colSpan={columns.length} className="h-24 text-center">
156 {t('table.no-result')}
157 </TableCell>
158 </TableRow>
159 )}
160 </TableBody>
161 </Table>
162
163 </div>
164 <DataTablePagination table={table} />
165 </div>
166 </div >
167 )
168}