| @@ -23,7 +23,7 @@ import { SessionWithTokens } from "@/config/authConfig"; | |||||
| import { createStockInLine } from "@/app/api/stockIn/actions"; | import { createStockInLine } from "@/app/api/stockIn/actions"; | ||||
| import { msg } from "../Swal/CustomAlerts"; | import { msg } from "../Swal/CustomAlerts"; | ||||
| import dayjs from "dayjs"; | import dayjs from "dayjs"; | ||||
| import { fetchInventories } from "@/app/api/inventory/actions"; | |||||
| //import { fetchInventories } from "@/app/api/inventory/actions"; | |||||
| import { InventoryResult } from "@/app/api/inventory"; | import { InventoryResult } from "@/app/api/inventory"; | ||||
| import { PrinterCombo } from "@/app/api/settings/printer"; | import { PrinterCombo } from "@/app/api/settings/printer"; | ||||
| import { JobTypeResponse } from "@/app/api/jo/actions"; | import { JobTypeResponse } from "@/app/api/jo/actions"; | ||||
| @@ -76,16 +76,21 @@ const JoSearch: React.FC<Props> = ({ defaultInputs, bomCombo, printerCombo, jobT | |||||
| useEffect(() => { | useEffect(() => { | ||||
| const fetchDetailedJos = async () => { | const fetchDetailedJos = async () => { | ||||
| const detailedMap = new Map<number, JobOrder>(); | const detailedMap = new Map<number, JobOrder>(); | ||||
| for (const jo of filteredJos) { | |||||
| try { | |||||
| const detailedJo = await fetchJoDetailClient(jo.id); | |||||
| detailedMap.set(jo.id, detailedJo); | |||||
| } catch (error) { | |||||
| console.error(`Error fetching detail for JO ${jo.id}:`, error); | |||||
| } | |||||
| try { | |||||
| const results = await Promise.all( | |||||
| filteredJos.map((jo) => | |||||
| fetchJoDetailClient(jo.id).then((detail) => ({ id: jo.id, detail })).catch((error) => { | |||||
| console.error(`Error fetching detail for JO ${jo.id}:`, error); | |||||
| return null; | |||||
| }) | |||||
| ) | |||||
| ); | |||||
| results.forEach((r) => { | |||||
| if (r) detailedMap.set(r.id, r.detail); | |||||
| }); | |||||
| } catch (error) { | |||||
| console.error("Error fetching JO details:", error); | |||||
| } | } | ||||
| setDetailedJos(detailedMap); | setDetailedJos(detailedMap); | ||||
| }; | }; | ||||
| @@ -93,7 +98,7 @@ const JoSearch: React.FC<Props> = ({ defaultInputs, bomCombo, printerCombo, jobT | |||||
| fetchDetailedJos(); | fetchDetailedJos(); | ||||
| } | } | ||||
| }, [filteredJos]); | }, [filteredJos]); | ||||
| /* | |||||
| useEffect(() => { | useEffect(() => { | ||||
| const fetchInventoryData = async () => { | const fetchInventoryData = async () => { | ||||
| try { | try { | ||||
| @@ -102,9 +107,9 @@ const JoSearch: React.FC<Props> = ({ defaultInputs, bomCombo, printerCombo, jobT | |||||
| name: "", | name: "", | ||||
| type: "", | type: "", | ||||
| pageNum: 0, | pageNum: 0, | ||||
| pageSize: 1000 | |||||
| pageSize: 200, | |||||
| }); | }); | ||||
| setInventoryData(inventoryResponse.records); | |||||
| setInventoryData(inventoryResponse.records ?? []); | |||||
| } catch (error) { | } catch (error) { | ||||
| console.error("Error fetching inventory data:", error); | console.error("Error fetching inventory data:", error); | ||||
| } | } | ||||
| @@ -112,6 +117,7 @@ const JoSearch: React.FC<Props> = ({ defaultInputs, bomCombo, printerCombo, jobT | |||||
| fetchInventoryData(); | fetchInventoryData(); | ||||
| }, []); | }, []); | ||||
| */ | |||||
| const getStockAvailable = (pickLine: JoDetailPickLine) => { | const getStockAvailable = (pickLine: JoDetailPickLine) => { | ||||
| const inventory = inventoryData.find(inventory => | const inventory = inventoryData.find(inventory => | ||||
| @@ -16,6 +16,8 @@ const JodetailSearchWrapper: React.FC & SubComponents = async () => { | |||||
| type: undefined, | type: undefined, | ||||
| status: undefined, | status: undefined, | ||||
| itemName: undefined, | itemName: undefined, | ||||
| pageNum: 0, | |||||
| pageSize: 50, | |||||
| }), | }), | ||||
| fetchPrinterCombo(), | fetchPrinterCombo(), | ||||
| ]); | ]); | ||||
| @@ -218,8 +218,10 @@ const JodetailSearch: React.FC<Props> = ({ pickOrders, printerCombo }) => { | |||||
| // 在组件加载时获取未分配订单 | // 在组件加载时获取未分配订单 | ||||
| useEffect(() => { | useEffect(() => { | ||||
| loadUnassignedOrders(); | |||||
| }, [loadUnassignedOrders]); | |||||
| if (tabIndex === 0) { | |||||
| loadUnassignedOrders(); | |||||
| } | |||||
| }, [tabIndex, loadUnassignedOrders]); | |||||
| const handleTabChange = useCallback<NonNullable<TabsProps["onChange"]>>( | const handleTabChange = useCallback<NonNullable<TabsProps["onChange"]>>( | ||||
| (_e, newValue) => { | (_e, newValue) => { | ||||
| @@ -525,7 +525,7 @@ const closeNewModal = useCallback(() => { | |||||
| width: 150, | width: 150, | ||||
| // flex: 0.5, | // flex: 0.5, | ||||
| renderCell: (params) => { | renderCell: (params) => { | ||||
| return params.row.uom?.udfudesc; | |||||
| return itemDetail.uom?.udfudesc; | |||||
| }, | }, | ||||
| }, | }, | ||||
| { | { | ||||
| @@ -220,7 +220,7 @@ const ProductProcessList: React.FC<ProductProcessListProps> = ({ onSelectProcess | |||||
| display: "flex", | display: "flex", | ||||
| flexDirection: "column", | flexDirection: "column", | ||||
| border: "1px solid", | border: "1px solid", | ||||
| borderColor: "success.main", | |||||
| borderColor: "blue", | |||||
| }} | }} | ||||
| > | > | ||||
| <CardContent | <CardContent | ||||
| @@ -240,8 +240,9 @@ const ProductProcessList: React.FC<ProductProcessListProps> = ({ onSelectProcess | |||||
| <Chip size="small" label={t(status)} color={statusColor as any} /> | <Chip size="small" label={t(status)} color={statusColor as any} /> | ||||
| </Stack> | </Stack> | ||||
| <Typography variant="body2" color="text.secondary"> | |||||
| {t("Item Name")}: {process.itemCode} {process.itemName} | |||||
| <Typography variant="subtitle1" color="blue"> | |||||
| {/* <strong>{t("Item Name")}:</strong> */} | |||||
| {process.itemCode} {process.itemName} | |||||
| </Typography> | </Typography> | ||||
| <Typography variant="body2" color="text.secondary"> | <Typography variant="body2" color="text.secondary"> | ||||
| {t("Production Priority")}: {process.productionPriority} | {t("Production Priority")}: {process.productionPriority} | ||||
| @@ -57,17 +57,16 @@ const style = { | |||||
| left: "50%", | left: "50%", | ||||
| transform: "translate(-50%, -50%)", | transform: "translate(-50%, -50%)", | ||||
| bgcolor: "background.paper", | bgcolor: "background.paper", | ||||
| pt: { xs: 0.5, sm: 1, md: 1.5 }, | |||||
| px: { xs: 1, sm: 1.5, md: 2 }, | |||||
| pb: { xs: 0.5, sm: 1, md: 1.5 }, | |||||
| width: { xs: "95%", sm: "85%", md: "75%", lg: "70%" }, | |||||
| maxWidth: "900px", | |||||
| maxHeight: { xs: "98vh", sm: "95vh", md: "90vh" }, | |||||
| pt: { xs: 0.5, sm: 0.75, md: 1 }, | |||||
| px: { xs: 1, sm: 1, md: 1.5 }, | |||||
| pb: { xs: 0.5, sm: 0.75, md: 1 }, | |||||
| width: { xs: "95%", sm: "72%", md: "60%", lg: "70%" }, | |||||
| maxWidth: "720px", | |||||
| maxHeight: { xs: "98vh", sm: "92vh", md: "88vh" }, | |||||
| overflow: "hidden", | overflow: "hidden", | ||||
| display: "flex", | display: "flex", | ||||
| flexDirection: "column", | flexDirection: "column", | ||||
| }; | }; | ||||
| const scannerStyle = { | const scannerStyle = { | ||||
| position: "absolute", | position: "absolute", | ||||
| top: "50%", | top: "50%", | ||||
| @@ -442,9 +441,9 @@ const PutAwayModal: React.FC<Props> = ({ open, onClose, warehouse, stockInLineId | |||||
| {itemDetail != undefined ? ( | {itemDetail != undefined ? ( | ||||
| <> | <> | ||||
| <Stack direction="column" justifyContent="flex-end" gap={0.25} sx={{ mb: 0.5 }}> | <Stack direction="column" justifyContent="flex-end" gap={0.25} sx={{ mb: 0.5 }}> | ||||
| <Typography variant="h4" sx={{ fontSize: { xs: "0.95rem", sm: "1.1rem", md: "1.3rem" }, mb: 0.25, lineHeight: 1.2 }}> | |||||
| 處理上架 | |||||
| </Typography> | |||||
| <Typography variant="h4" sx={{ fontSize: { xs: "0.95rem", sm: "0.95rem", md: "1.1rem" }, mb: 0.25, lineHeight: 1.2 }}> | |||||
| 處理上架 | |||||
| </Typography> | |||||
| <Box sx={{ "& .MuiFormControl-root": { mb: 0.5 }, "& .MuiTextField-root": { mb: 0.5 }, "& .MuiGrid-item": { mb: 0.25 } }}> | <Box sx={{ "& .MuiFormControl-root": { mb: 0.5 }, "& .MuiTextField-root": { mb: 0.5 }, "& .MuiGrid-item": { mb: 0.25 } }}> | ||||
| <Grid item xs={12}> | <Grid item xs={12}> | ||||
| {itemDetail.jobOrderId ? ( | {itemDetail.jobOrderId ? ( | ||||
| @@ -277,7 +277,7 @@ | |||||
| "Equipment Code": "設備編號", | "Equipment Code": "設備編號", | ||||
| "Seq": "步驟", | "Seq": "步驟", | ||||
| "SEQ": "步驟", | "SEQ": "步驟", | ||||
| "Item Name": "物料名稱", | |||||
| "Item Name": "產品名稱", | |||||
| "Job Order Info": "工單信息", | "Job Order Info": "工單信息", | ||||
| "Matching Stock": "工單對料", | "Matching Stock": "工單對料", | ||||
| "No data found": "沒有找到資料", | "No data found": "沒有找到資料", | ||||
| @@ -21,7 +21,7 @@ | |||||
| "Item-lotNo-ExpiryDate": "貨品-批號-到期日", | "Item-lotNo-ExpiryDate": "貨品-批號-到期日", | ||||
| "not available": "不可用", | "not available": "不可用", | ||||
| "Book Qty": "帳面庫存", | "Book Qty": "帳面庫存", | ||||
| "Submit Quantity": "提交數量", | |||||
| "Submit Quantity": "實際問題數量", | |||||
| "Batch Submit All": "批量提交所有", | "Batch Submit All": "批量提交所有", | ||||
| "Batch Save All": "批量保存所有", | "Batch Save All": "批量保存所有", | ||||
| "Batch Submit All": "批量提交所有", | "Batch Submit All": "批量提交所有", | ||||
| @@ -146,7 +146,7 @@ | |||||
| "Start QR Scan": "開始QR掃碼", | "Start QR Scan": "開始QR掃碼", | ||||
| "Stop QR Scan": "停止QR掃碼", | "Stop QR Scan": "停止QR掃碼", | ||||
| "Rows per page": "每頁行數", | "Rows per page": "每頁行數", | ||||
| "Job Order Item Name": "工單物料名稱", | |||||
| "Job Order Item Name": "工單產品名稱", | |||||
| "Job Order Code": "工單編號", | "Job Order Code": "工單編號", | ||||
| "View Details": "查看詳情", | "View Details": "查看詳情", | ||||
| "Skip": "跳過", | "Skip": "跳過", | ||||
| @@ -327,7 +327,7 @@ | |||||
| "acceptedQty": "接受數量", | "acceptedQty": "接受數量", | ||||
| "bind": "綁定", | "bind": "綁定", | ||||
| "expiryDate": "有效期", | "expiryDate": "有效期", | ||||
| "itemName": "物料名稱", | |||||
| "itemName": "產品名稱", | |||||
| "itemNo": "成品編號", | "itemNo": "成品編號", | ||||
| "not default warehosue": "不是默認倉庫", | "not default warehosue": "不是默認倉庫", | ||||
| "printQty": "打印數量", | "printQty": "打印數量", | ||||
| @@ -42,7 +42,7 @@ | |||||
| "Select Qc Item": "選擇品檢項目", | "Select Qc Item": "選擇品檢項目", | ||||
| "Select Type": "選擇類型", | "Select Type": "選擇類型", | ||||
| "Item Code": "物料編號", | "Item Code": "物料編號", | ||||
| "Item Name": "物料名稱", | |||||
| "Item Name": "產品名稱", | |||||
| "Qc Category Code": "品檢模板編號", | "Qc Category Code": "品檢模板編號", | ||||
| "Qc Category Name": "品檢模板名稱", | "Qc Category Name": "品檢模板名稱", | ||||
| "Qc Item Code": "品檢項目編號", | "Qc Item Code": "品檢項目編號", | ||||