FPSMS-frontend
選択できるのは25トピックまでです。 トピックは、先頭が英数字で、英数字とダッシュ('-')を使用した35文字以内のものにしてください。

ConsolidatedPickOrders.tsx 10 KiB

1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1ヶ月前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
1年前
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371
  1. import {
  2. Autocomplete,
  3. Box,
  4. Button,
  5. CircularProgress,
  6. FormControl,
  7. Grid,
  8. Modal,
  9. ModalProps,
  10. TextField,
  11. Typography,
  12. } from "@mui/material";
  13. import { GridToolbarContainer } from "@mui/x-data-grid";
  14. import {
  15. FooterPropsOverrides,
  16. GridColDef,
  17. GridRowSelectionModel,
  18. useGridApiRef,
  19. } from "@mui/x-data-grid";
  20. import { useCallback, useEffect, useMemo, useState } from "react";
  21. import { useTranslation } from "react-i18next";
  22. import StyledDataGrid from "../StyledDataGrid";
  23. import SearchResults, {
  24. Column,
  25. defaultPagingController,
  26. } from "../SearchResults/SearchResults";
  27. import {
  28. ByItemsSummary,
  29. ConsoPickOrderResult,
  30. PickOrderLine,
  31. PickOrderResult,
  32. } from "@/app/api/pickOrder";
  33. import { useRouter, useSearchParams } from "next/navigation";
  34. import ConsolidatePickOrderItemSum from "./ConsolidatePickOrderItemSum";
  35. import ConsolidatePickOrderSum from "./ConsolidatePickOrderSum";
  36. import { GridInputRowSelectionModel } from "@mui/x-data-grid";
  37. import {
  38. fetchConsoDetail,
  39. fetchConsoPickOrderClient,
  40. releasePickOrder,
  41. ReleasePickOrderInputs,
  42. } from "@/app/api/pickOrder/actions";
  43. import { EditNote } from "@mui/icons-material";
  44. import { fetchNameList, NameList } from "@/app/api/user/actions";
  45. import { useField } from "@mui/x-date-pickers/internals";
  46. import {
  47. FormProvider,
  48. SubmitErrorHandler,
  49. SubmitHandler,
  50. useForm,
  51. } from "react-hook-form";
  52. import { pickOrderStatusMap } from "@/app/utils/formatUtil";
  53. interface Props {
  54. filterArgs: Record<string, any>;
  55. }
  56. const style = {
  57. position: "absolute",
  58. top: "50%",
  59. left: "50%",
  60. transform: "translate(-50%, -50%)",
  61. bgcolor: "background.paper",
  62. pt: 5,
  63. px: 5,
  64. pb: 10,
  65. // width: 1500,
  66. width: { xs: "100%", sm: "100%", md: "100%" },
  67. };
  68. interface DisableButton {
  69. releaseBtn: boolean;
  70. removeBtn: boolean;
  71. }
  72. const ConsolidatedPickOrders: React.FC<Props> = ({ filterArgs }) => {
  73. const { t } = useTranslation("pickOrder");
  74. const router = useRouter();
  75. const apiRef = useGridApiRef();
  76. const [filteredPickOrders, setFilteredPickOrders] = useState(
  77. [] as ConsoPickOrderResult[],
  78. );
  79. const [isLoading, setIsLoading] = useState(false);
  80. const [modalOpen, setModalOpen] = useState(false); //change back to false
  81. const [consoCode, setConsoCode] = useState<string | undefined>(); ///change back to undefined
  82. const [revertIds, setRevertIds] = useState<GridInputRowSelectionModel>([]);
  83. const [totalCount, setTotalCount] = useState<number>();
  84. const [usernameList, setUsernameList] = useState<NameList[]>([]);
  85. const [byPickOrderRows, setByPickOrderRows] = useState<
  86. Omit<PickOrderResult, "items">[] | undefined
  87. >(undefined);
  88. const [byItemsRows, setByItemsRows] = useState<ByItemsSummary[] | undefined>(
  89. undefined,
  90. );
  91. const [disableRelease, setDisableRelease] = useState<boolean>(true);
  92. const formProps = useForm<ReleasePickOrderInputs>();
  93. const errors = formProps.formState.errors;
  94. const openDetailModal = useCallback((consoCode: string) => {
  95. setConsoCode(consoCode);
  96. setModalOpen(true);
  97. }, []);
  98. const closeDetailModal = useCallback(() => {
  99. setModalOpen(false);
  100. setConsoCode(undefined);
  101. }, []);
  102. const onDetailClick = useCallback(
  103. (pickOrder: any) => {
  104. console.log(pickOrder);
  105. const status = pickOrder.status;
  106. if (pickOrderStatusMap[status] >= 3) {
  107. router.push(`/pickOrder/detail?consoCode=${pickOrder.consoCode}`);
  108. } else {
  109. openDetailModal(pickOrder.consoCode);
  110. }
  111. },
  112. [router, openDetailModal],
  113. );
  114. const columns = useMemo<Column<ConsoPickOrderResult>[]>(
  115. () => [
  116. {
  117. name: "id",
  118. label: t("Detail"),
  119. onClick: onDetailClick,
  120. buttonIcon: <EditNote />,
  121. },
  122. {
  123. name: "consoCode",
  124. label: t("consoCode"),
  125. },
  126. {
  127. name: "status",
  128. label: t("status"),
  129. renderCell: (params: any) => t(params.status),
  130. },
  131. ],
  132. [onDetailClick, t],
  133. );
  134. const [pagingController, setPagingController] = useState(
  135. defaultPagingController,
  136. );
  137. // pass conso code back to assign
  138. // pass user back to assign
  139. const fetchNewPageConsoPickOrder = useCallback(
  140. async (
  141. pagingController: Record<string, number>,
  142. filterArgs: Record<string, number>,
  143. ) => {
  144. setIsLoading(true);
  145. const params = {
  146. ...pagingController,
  147. ...filterArgs,
  148. };
  149. const res = await fetchConsoPickOrderClient(params);
  150. if (res) {
  151. console.log(res);
  152. setFilteredPickOrders(res.records);
  153. setTotalCount(res.total);
  154. }
  155. setIsLoading(false);
  156. },
  157. [],
  158. );
  159. useEffect(() => {
  160. fetchNewPageConsoPickOrder(pagingController, filterArgs);
  161. }, [fetchNewPageConsoPickOrder, pagingController, filterArgs]);
  162. const isReleasable = useCallback((itemList: ByItemsSummary[]): boolean => {
  163. let isReleasable = true;
  164. for (const item of itemList) {
  165. isReleasable = item.requiredQty >= item.availableQty;
  166. if (!isReleasable) return isReleasable;
  167. }
  168. return isReleasable;
  169. }, []);
  170. const fetchConso = useCallback(
  171. async (consoCode: string) => {
  172. const res = await fetchConsoDetail(consoCode);
  173. const nameListRes = await fetchNameList();
  174. if (res) {
  175. console.log(res);
  176. setByPickOrderRows(res.pickOrders);
  177. // for testing
  178. // for (const item of res.items) {
  179. // item.availableQty = 1000;
  180. // }
  181. setByItemsRows(res.items);
  182. setDisableRelease(isReleasable(res.items));
  183. } else {
  184. console.log("error");
  185. console.log(res);
  186. }
  187. if (nameListRes) {
  188. console.log(nameListRes);
  189. setUsernameList(nameListRes);
  190. }
  191. },
  192. [isReleasable],
  193. );
  194. const closeHandler = useCallback<NonNullable<ModalProps["onClose"]>>(
  195. (...args) => {
  196. closeDetailModal();
  197. // reset();
  198. },
  199. [closeDetailModal],
  200. );
  201. const onChange = useCallback(
  202. (event: React.SyntheticEvent, newValue: NameList) => {
  203. console.log(newValue);
  204. formProps.setValue("assignTo", newValue.id);
  205. },
  206. [formProps],
  207. );
  208. const onSubmit = useCallback<SubmitHandler<ReleasePickOrderInputs>>(
  209. async (data, event) => {
  210. console.log(data);
  211. try {
  212. const res = await releasePickOrder(data);
  213. console.log(res);
  214. if (res.consoCode.length > 0) {
  215. console.log(res);
  216. router.push(`/pickOrder/detail?consoCode=${res.consoCode}`);
  217. } else {
  218. console.log(res);
  219. }
  220. } catch (error) {
  221. console.log(error);
  222. }
  223. },
  224. [router],
  225. );
  226. const onSubmitError = useCallback<SubmitErrorHandler<ReleasePickOrderInputs>>(
  227. (errors) => {},
  228. [],
  229. );
  230. const handleConsolidate_revert = useCallback(() => {
  231. console.log(revertIds);
  232. }, [revertIds]);
  233. useEffect(() => {
  234. if (consoCode) {
  235. fetchConso(consoCode);
  236. formProps.setValue("consoCode", consoCode);
  237. }
  238. }, [consoCode, fetchConso, formProps]);
  239. return (
  240. <>
  241. <Grid
  242. container
  243. rowGap={1}
  244. // direction="column"
  245. alignItems="center"
  246. justifyContent="center"
  247. >
  248. <Grid item xs={12}>
  249. {isLoading ? (
  250. <CircularProgress size={40} />
  251. ) : (
  252. <SearchResults<ConsoPickOrderResult>
  253. items={filteredPickOrders}
  254. columns={columns}
  255. pagingController={pagingController}
  256. setPagingController={setPagingController}
  257. totalCount={totalCount}
  258. />
  259. )}
  260. </Grid>
  261. </Grid>
  262. {consoCode != undefined ? (
  263. <Modal open={modalOpen} onClose={closeHandler}>
  264. <FormProvider {...formProps}>
  265. <Box
  266. sx={{ ...style, maxHeight: 800 }}
  267. component="form"
  268. onSubmit={formProps.handleSubmit(onSubmit, onSubmitError)}
  269. >
  270. <Grid container>
  271. <Grid item xs={8}>
  272. <Typography mb={2} variant="h4">
  273. {consoCode}
  274. </Typography>
  275. </Grid>
  276. <Grid
  277. item
  278. xs={4}
  279. display="flex"
  280. justifyContent="end"
  281. alignItems="end"
  282. >
  283. <FormControl fullWidth>
  284. <Autocomplete
  285. disableClearable
  286. fullWidth
  287. getOptionLabel={(option) => option.name}
  288. options={usernameList}
  289. onChange={onChange}
  290. renderInput={(params) => <TextField {...params} />}
  291. />
  292. </FormControl>
  293. </Grid>
  294. </Grid>
  295. <Box
  296. sx={{
  297. height: 400,
  298. overflowY: "auto",
  299. }}
  300. >
  301. <Grid container>
  302. <Grid item xs={12} sx={{ mt: 2 }}>
  303. <ConsolidatePickOrderSum
  304. rows={byPickOrderRows}
  305. setRows={setByPickOrderRows}
  306. consoCode={consoCode}
  307. revertIds={revertIds}
  308. setRevertIds={setRevertIds}
  309. />
  310. </Grid>
  311. <Grid item xs={12}>
  312. <ConsolidatePickOrderItemSum
  313. rows={byItemsRows}
  314. setRows={setByItemsRows}
  315. />
  316. </Grid>
  317. </Grid>
  318. </Box>
  319. <Grid container>
  320. <Grid
  321. item
  322. xs={12}
  323. display="flex"
  324. justifyContent="end"
  325. alignItems="end"
  326. >
  327. <Button
  328. disabled={(revertIds as number[]).length < 1}
  329. variant="outlined"
  330. onClick={handleConsolidate_revert}
  331. sx={{ mr: 1 }}
  332. >
  333. {t("remove")}
  334. </Button>
  335. <Button
  336. disabled={disableRelease}
  337. variant="outlined"
  338. // onClick={handleRelease}
  339. type="submit"
  340. >
  341. {t("release")}
  342. </Button>
  343. </Grid>
  344. </Grid>
  345. </Box>
  346. </FormProvider>
  347. </Modal>
  348. ) : undefined}
  349. </>
  350. );
  351. };
  352. export default ConsolidatedPickOrders;