trithuc-mvc-react 3.3.8 → 3.4.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/api/index.js +11 -0
- package/components/DataManagement/DataTable.jsx +31 -2
- package/components/DataManagement/DataTableSM.jsx +25 -2
- package/components/DataManagement/TableHead.jsx +33 -4
- package/components/DataManagement/TableRowRenderSM.jsx +1 -1
- package/components/DataManagement/index.jsx +17 -11
- package/package.json +1 -1
- package/utils/storage.js +9 -3
package/api/index.js
CHANGED
|
@@ -235,6 +235,17 @@ export const exportExcel = async ({ tableName, data }) => {
|
|
|
235
235
|
};
|
|
236
236
|
|
|
237
237
|
export const uploadFile = async (formData) => {
|
|
238
|
+
// 1. Lấy URL hiện tại
|
|
239
|
+
const currentUrl = window.location.href;
|
|
240
|
+
|
|
241
|
+
// 2. Append vào formData
|
|
242
|
+
formData.append("currentUrl", currentUrl);
|
|
243
|
+
|
|
244
|
+
// 3. Log tất cả key-value trong FormData để kiểm tra
|
|
245
|
+
// console.log("===== FormData Contents =====");
|
|
246
|
+
// formData.forEach((value, key) => {
|
|
247
|
+
// console.log(key, value);
|
|
248
|
+
// });
|
|
238
249
|
if (!apiUrl) {
|
|
239
250
|
const res = await api.post(`${getBaseUrl()}/Handler/fileUploader.ashx`, formData, {
|
|
240
251
|
headers: {
|
|
@@ -46,15 +46,38 @@ const DataTable = ({ multipleActions = [], page, setPage = () => {}, disableEdit
|
|
|
46
46
|
const [rowsPerPage, setRowsPerPage] = useState(defaultRowsPerPage);
|
|
47
47
|
const [openDialog, setOpenDialog] = useState(false);
|
|
48
48
|
const [deleteId, setDeleteId] = useState(null);
|
|
49
|
+
const defaultSortColumn = columns.find((c) => c.defaultSort);
|
|
50
|
+
|
|
51
|
+
const [orderBy, setOrderBy] = useState(defaultSortColumn?.field || "");
|
|
52
|
+
const [order, setOrder] = useState(defaultSortColumn?.defaultOrder || "asc");
|
|
53
|
+
useEffect(() => {
|
|
54
|
+
const defaultSortColumn = columns.find((c) => c.defaultSort);
|
|
55
|
+
if (defaultSortColumn) {
|
|
56
|
+
setOrderBy(defaultSortColumn.field);
|
|
57
|
+
setOrder(defaultSortColumn.defaultOrder || "asc");
|
|
58
|
+
}
|
|
59
|
+
}, [columns]);
|
|
60
|
+
|
|
61
|
+
const handleRequestSort = (event, property) => {
|
|
62
|
+
const isAsc = orderBy === property && order === "asc";
|
|
63
|
+
setOrder(isAsc ? "desc" : "asc");
|
|
64
|
+
setOrderBy(property);
|
|
65
|
+
};
|
|
49
66
|
|
|
50
67
|
const { data, isLoading } = useQuery({
|
|
51
|
-
queryKey: [tableName, page, rowsPerPage, dataSearch],
|
|
68
|
+
queryKey: [tableName, page, rowsPerPage, dataSearch, order, orderBy],
|
|
52
69
|
queryFn: () =>
|
|
53
70
|
getDatasFromTable({
|
|
54
71
|
tableName: tableName,
|
|
55
72
|
page: page + 1,
|
|
56
73
|
pageSize: rowsPerPage,
|
|
57
|
-
data:
|
|
74
|
+
data: {
|
|
75
|
+
...dataSearch,
|
|
76
|
+
...(orderBy && {
|
|
77
|
+
SortBy: orderBy,
|
|
78
|
+
IsDescending: order === "desc"
|
|
79
|
+
})
|
|
80
|
+
}
|
|
58
81
|
}),
|
|
59
82
|
defaultQueryOptions,
|
|
60
83
|
// keepPreviousData: true,
|
|
@@ -73,6 +96,7 @@ const DataTable = ({ multipleActions = [], page, setPage = () => {}, disableEdit
|
|
|
73
96
|
}
|
|
74
97
|
}
|
|
75
98
|
});
|
|
99
|
+
|
|
76
100
|
const changeStatusMutation = useMutation(changeStatusDataToTable, {
|
|
77
101
|
onSuccess: ({ status = false, message = " Có lỗi xảy ra !" }) => {
|
|
78
102
|
if (URL_APPLICATION_API) {
|
|
@@ -253,6 +277,7 @@ const DataTable = ({ multipleActions = [], page, setPage = () => {}, disableEdit
|
|
|
253
277
|
}
|
|
254
278
|
setOpenDeleteMultipleDialog(false); // Đóng Dialog sau khi chọn
|
|
255
279
|
};
|
|
280
|
+
|
|
256
281
|
const theme = useTheme();
|
|
257
282
|
const downXL = useMediaQuery(theme.breakpoints.down("xl"));
|
|
258
283
|
|
|
@@ -283,7 +308,11 @@ const DataTable = ({ multipleActions = [], page, setPage = () => {}, disableEdit
|
|
|
283
308
|
onSelectAllClick={handleSelectAllClick}
|
|
284
309
|
numSelected={selectedItems?.length}
|
|
285
310
|
rowCount={rows.length}
|
|
311
|
+
order={order}
|
|
312
|
+
orderBy={orderBy}
|
|
313
|
+
onRequestSort={handleRequestSort}
|
|
286
314
|
/>
|
|
315
|
+
|
|
287
316
|
{isLoading ? (
|
|
288
317
|
<TableBody>
|
|
289
318
|
<TableRowsLoader rowsNum={15} colsNum={columns.length + 3} />
|
|
@@ -45,15 +45,38 @@ const DataTableSM = ({ multipleActions = [], page, setPage = () => {}, disableEd
|
|
|
45
45
|
const [rowsPerPage, setRowsPerPage] = useState(defaultRowsPerPage);
|
|
46
46
|
const [openDialog, setOpenDialog] = useState(false);
|
|
47
47
|
const [deleteId, setDeleteId] = useState(null);
|
|
48
|
+
const defaultSortColumn = columns.find((c) => c.defaultSort);
|
|
49
|
+
|
|
50
|
+
const [orderBy, setOrderBy] = useState(defaultSortColumn?.field || "");
|
|
51
|
+
const [order, setOrder] = useState(defaultSortColumn?.defaultOrder || "asc");
|
|
52
|
+
useEffect(() => {
|
|
53
|
+
const defaultSortColumn = columns.find((c) => c.defaultSort);
|
|
54
|
+
if (defaultSortColumn) {
|
|
55
|
+
setOrderBy(defaultSortColumn.field);
|
|
56
|
+
setOrder(defaultSortColumn.defaultOrder || "asc");
|
|
57
|
+
}
|
|
58
|
+
}, [columns]);
|
|
59
|
+
|
|
60
|
+
const handleRequestSort = (event, property) => {
|
|
61
|
+
const isAsc = orderBy === property && order === "asc";
|
|
62
|
+
setOrder(isAsc ? "desc" : "asc");
|
|
63
|
+
setOrderBy(property);
|
|
64
|
+
};
|
|
48
65
|
|
|
49
66
|
const { data, isLoading } = useQuery({
|
|
50
|
-
queryKey: [tableName, page, rowsPerPage, dataSearch],
|
|
67
|
+
queryKey: [tableName, page, rowsPerPage, dataSearch, order, orderBy],
|
|
51
68
|
queryFn: () =>
|
|
52
69
|
getDatasFromTable({
|
|
53
70
|
tableName: tableName,
|
|
54
71
|
page: page + 1,
|
|
55
72
|
pageSize: rowsPerPage,
|
|
56
|
-
data:
|
|
73
|
+
data: {
|
|
74
|
+
...dataSearch,
|
|
75
|
+
...(orderBy && {
|
|
76
|
+
SortBy: orderBy,
|
|
77
|
+
IsDescending: order === "desc"
|
|
78
|
+
})
|
|
79
|
+
}
|
|
57
80
|
}),
|
|
58
81
|
defaultQueryOptions,
|
|
59
82
|
// keepPreviousData: true,
|
|
@@ -1,15 +1,22 @@
|
|
|
1
|
-
import { Checkbox, TableHead as MuiTableHead, TableCell, TableRow, useMediaQuery, useTheme } from "@mui/material";
|
|
1
|
+
import { Checkbox, TableHead as MuiTableHead, TableCell, TableRow, TableSortLabel, useMediaQuery, useTheme } from "@mui/material";
|
|
2
2
|
import { usePermission } from "../../hooks";
|
|
3
3
|
import { useDataTable } from "./hooks";
|
|
4
|
-
|
|
4
|
+
|
|
5
|
+
export function TableHead({ numSelected, rowCount, onSelectAllClick, headLabel, order, orderBy, onRequestSort }) {
|
|
5
6
|
const { disableStatus, disableCellThaoTac, tableName } = useDataTable();
|
|
6
7
|
const { canEdit } = usePermission(tableName);
|
|
7
8
|
|
|
8
9
|
const theme = useTheme();
|
|
9
10
|
const downXl = useMediaQuery(theme.breakpoints.down("xl"));
|
|
11
|
+
|
|
12
|
+
const createSortHandler = (property) => (event) => {
|
|
13
|
+
onRequestSort(event, property);
|
|
14
|
+
};
|
|
15
|
+
|
|
10
16
|
return (
|
|
11
17
|
<MuiTableHead sx={{ height: 56, visibility: numSelected > 0 ? "hidden" : "visible" }}>
|
|
12
18
|
<TableRow>
|
|
19
|
+
{/* Checkbox chọn tất cả */}
|
|
13
20
|
<TableCell padding="checkbox">
|
|
14
21
|
<Checkbox
|
|
15
22
|
indeterminate={numSelected > 0 && numSelected < rowCount}
|
|
@@ -18,13 +25,35 @@ export function TableHead({ numSelected, rowCount, onSelectAllClick, headLabel }
|
|
|
18
25
|
onChange={onSelectAllClick}
|
|
19
26
|
/>
|
|
20
27
|
</TableCell>
|
|
28
|
+
|
|
29
|
+
{/* STT không sort */}
|
|
21
30
|
<TableCell sx={{ textAlign: "center" }}>STT</TableCell>
|
|
31
|
+
|
|
32
|
+
{/* Các cột động */}
|
|
22
33
|
{headLabel.map((headCell) => (
|
|
23
|
-
<TableCell
|
|
24
|
-
{headCell.
|
|
34
|
+
<TableCell
|
|
35
|
+
key={headCell.field}
|
|
36
|
+
align={headCell.alignRight ? "right" : "left"}
|
|
37
|
+
sortDirection={orderBy === headCell.field ? order : false}
|
|
38
|
+
>
|
|
39
|
+
{headCell.sortable ? (
|
|
40
|
+
<TableSortLabel
|
|
41
|
+
active={orderBy === headCell.field}
|
|
42
|
+
direction={orderBy === headCell.field ? order : "asc"}
|
|
43
|
+
onClick={createSortHandler(headCell.field)}
|
|
44
|
+
>
|
|
45
|
+
{headCell.label}
|
|
46
|
+
</TableSortLabel>
|
|
47
|
+
) : (
|
|
48
|
+
headCell.label
|
|
49
|
+
)}
|
|
25
50
|
</TableCell>
|
|
26
51
|
))}
|
|
52
|
+
|
|
53
|
+
{/* Kích hoạt */}
|
|
27
54
|
{!disableStatus && canEdit && <TableCell sx={{ textAlign: "center" }}>Kích hoạt</TableCell>}
|
|
55
|
+
|
|
56
|
+
{/* Thao tác */}
|
|
28
57
|
{!disableCellThaoTac && <TableCell sx={{ minWidth: "136px", textAlign: "center" }}>Thao tác</TableCell>}
|
|
29
58
|
</TableRow>
|
|
30
59
|
</MuiTableHead>
|
|
@@ -67,7 +67,8 @@ DataManagement.propTypes = {
|
|
|
67
67
|
titleAddButton: PropTypes.string,
|
|
68
68
|
thongKe: PropTypes.object,
|
|
69
69
|
bieuDo: PropTypes.object,
|
|
70
|
-
disableHead: PropTypes.bool
|
|
70
|
+
disableHead: PropTypes.bool,
|
|
71
|
+
disableSearch: PropTypes.bool
|
|
71
72
|
};
|
|
72
73
|
const getDefaultValues = (filters = []) => {
|
|
73
74
|
const defaultValues = {};
|
|
@@ -112,7 +113,8 @@ function DataManagement({
|
|
|
112
113
|
titleAddButton = "Thêm mới",
|
|
113
114
|
thongKe,
|
|
114
115
|
bieuDo,
|
|
115
|
-
disableHead = false
|
|
116
|
+
disableHead = false,
|
|
117
|
+
disableSearch = false
|
|
116
118
|
}) {
|
|
117
119
|
const [openEditorDialog, setOpenEditorDialog] = useState(false);
|
|
118
120
|
const [selectedEditItem, setSelectedEditItem] = useState(null);
|
|
@@ -189,7 +191,8 @@ function DataManagement({
|
|
|
189
191
|
titleAddButton,
|
|
190
192
|
thongKe,
|
|
191
193
|
bieuDo,
|
|
192
|
-
disableHead
|
|
194
|
+
disableHead,
|
|
195
|
+
disableSearch
|
|
193
196
|
};
|
|
194
197
|
}, [
|
|
195
198
|
reserPage,
|
|
@@ -211,7 +214,8 @@ function DataManagement({
|
|
|
211
214
|
defaultRowsPerPage,
|
|
212
215
|
thongKe,
|
|
213
216
|
bieuDo,
|
|
214
|
-
disableHead
|
|
217
|
+
disableHead,
|
|
218
|
+
disableSearch
|
|
215
219
|
]);
|
|
216
220
|
const methods = useForm({ defaultValues: getDefaultValues(filters) });
|
|
217
221
|
const { reset, setValue } = methods;
|
|
@@ -426,13 +430,15 @@ function DataManagement({
|
|
|
426
430
|
{tabPanel}
|
|
427
431
|
{viewMode === "table" && (
|
|
428
432
|
<>
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
433
|
+
{!disableSearch && (
|
|
434
|
+
<FilterGod
|
|
435
|
+
tableName={tableName}
|
|
436
|
+
filters={filters}
|
|
437
|
+
filterButtons={filterButtons}
|
|
438
|
+
elementSize={elementSize}
|
|
439
|
+
setPage={setPage}
|
|
440
|
+
/>
|
|
441
|
+
)}
|
|
436
442
|
{backParentNavigator}
|
|
437
443
|
{!isSmallScreen ? (
|
|
438
444
|
<DataTable
|
package/package.json
CHANGED
package/utils/storage.js
CHANGED
|
@@ -142,11 +142,9 @@ export const storeSetCurrentInfor = (data) => {
|
|
|
142
142
|
const storedThamSo = storedUserInfo?.ThamSoHeThong?.find((item) => item.TenThamSo === "DEFAULT_ROWS_PER_PAGE");
|
|
143
143
|
const newThamSo = data?.ThamSoHeThong?.find((item) => item.TenThamSo === "DEFAULT_ROWS_PER_PAGE");
|
|
144
144
|
|
|
145
|
-
// Kiểm tra và cập nhật nếu thông tin mới từ API
|
|
146
145
|
if (newThamSo) {
|
|
147
146
|
const isUpdated = !storedThamSo || new Date(newThamSo.ModifiedDate) > new Date(storedThamSo?.ModifiedDate);
|
|
148
147
|
if (isUpdated) {
|
|
149
|
-
// Xóa dữ liệu `rowsPerPage` cũ từ localStorage nếu cần
|
|
150
148
|
Object.keys(localStorage).forEach((key) => {
|
|
151
149
|
if (key.endsWith("rowsPerPage")) {
|
|
152
150
|
localStorage.removeItem(key);
|
|
@@ -155,10 +153,18 @@ export const storeSetCurrentInfor = (data) => {
|
|
|
155
153
|
}
|
|
156
154
|
}
|
|
157
155
|
|
|
158
|
-
// Mã hóa dữ liệu và lưu vào localStorage
|
|
159
156
|
try {
|
|
160
157
|
const encryptedData = encryptData(data);
|
|
161
158
|
localStorage.setItem("GetCurrentInfor", encryptedData);
|
|
159
|
+
|
|
160
|
+
// 🔹 Bắn event cho từng tham số hệ thống
|
|
161
|
+
data?.ThamSoHeThong?.forEach((item) => {
|
|
162
|
+
window.dispatchEvent(
|
|
163
|
+
new CustomEvent("GetCurrentInfor-changed", {
|
|
164
|
+
detail: { key: item.TenThamSo, value: item.GiaTri }
|
|
165
|
+
})
|
|
166
|
+
);
|
|
167
|
+
});
|
|
162
168
|
} catch (error) {
|
|
163
169
|
console.error("Error encrypting or saving data to localStorage:", error);
|
|
164
170
|
}
|