@optifye/dashboard-core 6.1.0 → 6.1.5
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/dist/index.js +101 -163
- package/dist/index.mjs +101 -163
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -32591,69 +32591,119 @@ var TargetsView = ({
|
|
|
32591
32591
|
const { skus, isLoading: skusLoading } = useSKUs(companyId);
|
|
32592
32592
|
const skuEnabled = dashboardConfig?.skuConfig?.enabled || false;
|
|
32593
32593
|
React19.useEffect(() => {
|
|
32594
|
-
|
|
32594
|
+
let timeoutId;
|
|
32595
|
+
let retryCount = 0;
|
|
32596
|
+
const MAX_RETRIES2 = 2;
|
|
32597
|
+
const LOADING_TIMEOUT = 15e3;
|
|
32598
|
+
const fetchInitialData = async () => {
|
|
32595
32599
|
if (!supabase || lineIds.length === 0) return;
|
|
32596
|
-
|
|
32597
|
-
|
|
32598
|
-
|
|
32599
|
-
|
|
32600
|
-
|
|
32601
|
-
|
|
32602
|
-
|
|
32603
|
-
|
|
32604
|
-
}
|
|
32605
|
-
|
|
32606
|
-
|
|
32600
|
+
setIsLoading(true);
|
|
32601
|
+
timeoutId = setTimeout(() => {
|
|
32602
|
+
console.error("Loading timeout reached");
|
|
32603
|
+
if (retryCount < MAX_RETRIES2) {
|
|
32604
|
+
retryCount++;
|
|
32605
|
+
console.log(`Retrying... (attempt ${retryCount + 1}/${MAX_RETRIES2 + 1})`);
|
|
32606
|
+
sonner.toast.warning("Loading is taking longer than expected. Retrying...");
|
|
32607
|
+
fetchInitialData();
|
|
32608
|
+
} else {
|
|
32609
|
+
setIsLoading(false);
|
|
32610
|
+
sonner.toast.error("Failed to load data. Please refresh the page.");
|
|
32607
32611
|
}
|
|
32608
|
-
});
|
|
32609
|
-
const results = await Promise.all(detailsPromises);
|
|
32610
|
-
setLineWorkspaces((prev) => {
|
|
32611
|
-
const newWorkspaces = { ...prev };
|
|
32612
|
-
let needsUpdate = false;
|
|
32613
|
-
results.forEach((result) => {
|
|
32614
|
-
if (result.factoryId && newWorkspaces[result.lineId] && newWorkspaces[result.lineId].factoryId !== result.factoryId) {
|
|
32615
|
-
newWorkspaces[result.lineId].factoryId = result.factoryId;
|
|
32616
|
-
needsUpdate = true;
|
|
32617
|
-
}
|
|
32618
|
-
});
|
|
32619
|
-
return needsUpdate ? newWorkspaces : prev;
|
|
32620
|
-
});
|
|
32621
|
-
};
|
|
32622
|
-
fetchLineDetails();
|
|
32623
|
-
}, [supabase, lineIds]);
|
|
32624
|
-
React19.useEffect(() => {
|
|
32625
|
-
const fetchActions = async () => {
|
|
32626
|
-
if (!supabase) {
|
|
32627
|
-
console.error("Supabase client not available in fetchActions");
|
|
32628
|
-
sonner.toast.error("Initialization error, please refresh.");
|
|
32629
|
-
return;
|
|
32630
|
-
}
|
|
32612
|
+
}, LOADING_TIMEOUT);
|
|
32631
32613
|
try {
|
|
32632
|
-
const actions = await
|
|
32633
|
-
|
|
32634
|
-
|
|
32635
|
-
|
|
32614
|
+
const [factoryResults, actions] = await Promise.all([
|
|
32615
|
+
// Fetch factory IDs
|
|
32616
|
+
Promise.all(lineIds.map(async (lineId) => {
|
|
32617
|
+
try {
|
|
32618
|
+
const { data, error } = await supabase.from("lines").select("factory_id").eq("id", lineId).single();
|
|
32619
|
+
if (error) {
|
|
32620
|
+
console.error(`Error fetching factory_id for line ${lineId}:`, error);
|
|
32621
|
+
return { lineId, factoryId: void 0 };
|
|
32622
|
+
}
|
|
32623
|
+
return { lineId, factoryId: data?.factory_id };
|
|
32624
|
+
} catch (err) {
|
|
32625
|
+
console.error(`Exception fetching factory_id for line ${lineId}:`, err);
|
|
32626
|
+
return { lineId, factoryId: void 0 };
|
|
32627
|
+
}
|
|
32628
|
+
})),
|
|
32629
|
+
// Fetch action IDs
|
|
32630
|
+
actionService.getActionsByName(
|
|
32631
|
+
[ACTION_NAMES.ASSEMBLY, ACTION_NAMES.PACKAGING],
|
|
32632
|
+
companyId
|
|
32633
|
+
)
|
|
32634
|
+
]);
|
|
32636
32635
|
const assemblyAction = actions.find((a) => a.action_name === ACTION_NAMES.ASSEMBLY);
|
|
32637
32636
|
const packagingAction = actions.find((a) => a.action_name === ACTION_NAMES.PACKAGING);
|
|
32638
32637
|
if (!assemblyAction || !packagingAction) {
|
|
32639
32638
|
throw new Error("Could not find required actions");
|
|
32640
32639
|
}
|
|
32641
|
-
const
|
|
32640
|
+
const actionIdsData = {
|
|
32642
32641
|
assembly: assemblyAction.id,
|
|
32643
32642
|
packaging: packagingAction.id
|
|
32644
32643
|
};
|
|
32645
|
-
|
|
32646
|
-
|
|
32647
|
-
|
|
32644
|
+
setActionIds(actionIdsData);
|
|
32645
|
+
const updatedLineWorkspaces = { ...initialLineWorkspaces };
|
|
32646
|
+
factoryResults.forEach((result) => {
|
|
32647
|
+
if (result.factoryId && updatedLineWorkspaces[result.lineId]) {
|
|
32648
|
+
updatedLineWorkspaces[result.lineId].factoryId = result.factoryId;
|
|
32649
|
+
}
|
|
32648
32650
|
});
|
|
32649
|
-
|
|
32651
|
+
const currentDate = getOperationalDate();
|
|
32652
|
+
for (const lineId of lineIds) {
|
|
32653
|
+
if (!updatedLineWorkspaces[lineId]?.factoryId) {
|
|
32654
|
+
console.warn(`Skipping workspace fetch for line ${lineId} - no factory ID`);
|
|
32655
|
+
continue;
|
|
32656
|
+
}
|
|
32657
|
+
try {
|
|
32658
|
+
const workspacesData = await workspaceService.getWorkspaces(lineId);
|
|
32659
|
+
const actionThresholds = await workspaceService.getActionThresholds(
|
|
32660
|
+
lineId,
|
|
32661
|
+
currentDate,
|
|
32662
|
+
selectedShift
|
|
32663
|
+
);
|
|
32664
|
+
const mappedWorkspaces = workspacesData.map((ws) => {
|
|
32665
|
+
const threshold = actionThresholds.find((t) => t.workspace_id === ws.id);
|
|
32666
|
+
return {
|
|
32667
|
+
id: ws.id,
|
|
32668
|
+
name: ws.workspace_id,
|
|
32669
|
+
targetPPH: threshold?.pph_threshold ?? (ws.action_pph_threshold === null ? "" : ws.action_pph_threshold),
|
|
32670
|
+
targetCycleTime: threshold?.ideal_cycle_time ?? (ws.action_cycle_time === null ? "" : ws.action_cycle_time),
|
|
32671
|
+
targetDayOutput: threshold?.total_day_output ?? (ws.action_total_day_output === null ? "" : ws.action_total_day_output),
|
|
32672
|
+
actionType: ws.action_id === actionIdsData.assembly ? "assembly" : ws.action_id === actionIdsData.packaging ? "packaging" : "assembly",
|
|
32673
|
+
actionId: ws.action_id === actionIdsData.assembly ? actionIdsData.assembly : ws.action_id === actionIdsData.packaging ? actionIdsData.packaging : actionIdsData.assembly
|
|
32674
|
+
};
|
|
32675
|
+
}).sort((a, b) => a.name.localeCompare(b.name, void 0, { numeric: true }));
|
|
32676
|
+
updatedLineWorkspaces[lineId].workspaces = mappedWorkspaces;
|
|
32677
|
+
} catch (error) {
|
|
32678
|
+
console.error(`Error fetching workspace data for line ${lineId}:`, error);
|
|
32679
|
+
}
|
|
32680
|
+
}
|
|
32681
|
+
setLineWorkspaces(updatedLineWorkspaces);
|
|
32682
|
+
await fetchAllShiftsData(updatedLineWorkspaces);
|
|
32650
32683
|
} catch (error) {
|
|
32651
|
-
console.error("Error fetching
|
|
32652
|
-
|
|
32684
|
+
console.error("Error fetching initial data:", error);
|
|
32685
|
+
clearTimeout(timeoutId);
|
|
32686
|
+
if (retryCount < MAX_RETRIES2) {
|
|
32687
|
+
retryCount++;
|
|
32688
|
+
console.log(`Error occurred, retrying... (attempt ${retryCount + 1}/${MAX_RETRIES2 + 1})`);
|
|
32689
|
+
sonner.toast.warning("Error loading data. Retrying...");
|
|
32690
|
+
setTimeout(() => fetchInitialData(), 1e3);
|
|
32691
|
+
} else {
|
|
32692
|
+
sonner.toast.error("Failed to load initial data");
|
|
32693
|
+
setIsLoading(false);
|
|
32694
|
+
}
|
|
32695
|
+
} finally {
|
|
32696
|
+
clearTimeout(timeoutId);
|
|
32697
|
+
if (retryCount === 0 || retryCount >= MAX_RETRIES2) {
|
|
32698
|
+
setIsLoading(false);
|
|
32699
|
+
}
|
|
32653
32700
|
}
|
|
32654
32701
|
};
|
|
32655
|
-
|
|
32656
|
-
|
|
32702
|
+
fetchInitialData();
|
|
32703
|
+
return () => {
|
|
32704
|
+
clearTimeout(timeoutId);
|
|
32705
|
+
};
|
|
32706
|
+
}, [supabase, lineIds, companyId]);
|
|
32657
32707
|
React19.useCallback(async (shiftId) => {
|
|
32658
32708
|
try {
|
|
32659
32709
|
if (!supabase) return;
|
|
@@ -32896,92 +32946,6 @@ var TargetsView = ({
|
|
|
32896
32946
|
};
|
|
32897
32947
|
}
|
|
32898
32948
|
}, [supabase]);
|
|
32899
|
-
React19.useEffect(() => {
|
|
32900
|
-
const allFactoryIdsLoaded = lineIds.every((lineId) => lineWorkspaces[lineId]?.factoryId);
|
|
32901
|
-
if (!actionIds || !allFactoryIdsLoaded) {
|
|
32902
|
-
return;
|
|
32903
|
-
}
|
|
32904
|
-
const workspacesAlreadyLoadedForAnyLine = Object.values(lineWorkspaces).some(
|
|
32905
|
-
(line) => line.workspaces && line.workspaces.length > 0
|
|
32906
|
-
);
|
|
32907
|
-
if (workspacesAlreadyLoadedForAnyLine) {
|
|
32908
|
-
setIsLoading(false);
|
|
32909
|
-
return;
|
|
32910
|
-
}
|
|
32911
|
-
const fetchWorkspacesAndThenThresholds = async () => {
|
|
32912
|
-
setIsLoading(true);
|
|
32913
|
-
try {
|
|
32914
|
-
if (!supabase) {
|
|
32915
|
-
sonner.toast.error("Supabase client not available");
|
|
32916
|
-
setIsLoading(false);
|
|
32917
|
-
return;
|
|
32918
|
-
}
|
|
32919
|
-
console.log("Starting workspace fetch with actionIds and loaded factoryIds.");
|
|
32920
|
-
const newUpdatedLineWorkspaces = { ...lineWorkspaces };
|
|
32921
|
-
let workspacesHaveBeenUpdated = false;
|
|
32922
|
-
for (const lineId of lineIds) {
|
|
32923
|
-
if (!newUpdatedLineWorkspaces[lineId]?.factoryId) {
|
|
32924
|
-
console.warn(`FactoryId for line ${lineId} missing during workspace fetch. Skipping its workspaces.`);
|
|
32925
|
-
continue;
|
|
32926
|
-
}
|
|
32927
|
-
try {
|
|
32928
|
-
const fetchedLineWorkspacesData = await workspaceService.getWorkspaces(lineId);
|
|
32929
|
-
let mappedWorkspaces = fetchedLineWorkspacesData.map((ws) => ({
|
|
32930
|
-
id: ws.id,
|
|
32931
|
-
name: ws.workspace_id,
|
|
32932
|
-
targetPPH: ws.action_pph_threshold === null ? "" : ws.action_pph_threshold,
|
|
32933
|
-
targetCycleTime: ws.action_cycle_time === null ? "" : ws.action_cycle_time,
|
|
32934
|
-
targetDayOutput: ws.action_total_day_output === null ? "" : ws.action_total_day_output,
|
|
32935
|
-
actionType: ws.action_id === actionIds.assembly ? "assembly" : ws.action_id === actionIds.packaging ? "packaging" : "assembly",
|
|
32936
|
-
actionId: ws.action_id === actionIds.assembly ? actionIds.assembly : ws.action_id === actionIds.packaging ? actionIds.packaging : actionIds.assembly
|
|
32937
|
-
})).sort((a, b) => a.name.localeCompare(b.name, void 0, { numeric: true }));
|
|
32938
|
-
const currentDate = getOperationalDate();
|
|
32939
|
-
try {
|
|
32940
|
-
const actionThresholds = await workspaceService.getActionThresholds(
|
|
32941
|
-
lineId,
|
|
32942
|
-
currentDate,
|
|
32943
|
-
selectedShift
|
|
32944
|
-
);
|
|
32945
|
-
mappedWorkspaces = mappedWorkspaces.map((ws) => {
|
|
32946
|
-
const threshold = actionThresholds.find((t) => t.workspace_id === ws.id);
|
|
32947
|
-
if (threshold) {
|
|
32948
|
-
return {
|
|
32949
|
-
...ws,
|
|
32950
|
-
targetPPH: threshold.pph_threshold,
|
|
32951
|
-
targetCycleTime: threshold.ideal_cycle_time,
|
|
32952
|
-
targetDayOutput: threshold.total_day_output
|
|
32953
|
-
};
|
|
32954
|
-
}
|
|
32955
|
-
return ws;
|
|
32956
|
-
});
|
|
32957
|
-
console.log(`Merged action thresholds for line ${lineId}, found ${actionThresholds.length} saved thresholds`);
|
|
32958
|
-
} catch (error) {
|
|
32959
|
-
console.error(`Error fetching action thresholds for line ${lineId}:`, error);
|
|
32960
|
-
}
|
|
32961
|
-
if (JSON.stringify(mappedWorkspaces) !== JSON.stringify(newUpdatedLineWorkspaces[lineId].workspaces)) {
|
|
32962
|
-
newUpdatedLineWorkspaces[lineId] = {
|
|
32963
|
-
...newUpdatedLineWorkspaces[lineId],
|
|
32964
|
-
workspaces: mappedWorkspaces
|
|
32965
|
-
};
|
|
32966
|
-
workspacesHaveBeenUpdated = true;
|
|
32967
|
-
}
|
|
32968
|
-
} catch (error) {
|
|
32969
|
-
console.error(`Error fetching workspaces for line ${lineId}:`, error);
|
|
32970
|
-
}
|
|
32971
|
-
}
|
|
32972
|
-
if (workspacesHaveBeenUpdated) {
|
|
32973
|
-
setLineWorkspaces(newUpdatedLineWorkspaces);
|
|
32974
|
-
}
|
|
32975
|
-
await fetchAllShiftsData(newUpdatedLineWorkspaces);
|
|
32976
|
-
} catch (error) {
|
|
32977
|
-
console.error("Error in fetchWorkspacesAndThenThresholds:", error);
|
|
32978
|
-
sonner.toast.error("Failed to load workspace data");
|
|
32979
|
-
} finally {
|
|
32980
|
-
setIsLoading(false);
|
|
32981
|
-
}
|
|
32982
|
-
};
|
|
32983
|
-
fetchWorkspacesAndThenThresholds();
|
|
32984
|
-
}, [actionIds, supabase, lineIds]);
|
|
32985
32949
|
const toggleLineDropdown = React19.useCallback((lineId) => {
|
|
32986
32950
|
setLineWorkspaces((prev) => {
|
|
32987
32951
|
const newIsOpen = !prev[lineId].isOpen;
|
|
@@ -33208,14 +33172,15 @@ var TargetsView = ({
|
|
|
33208
33172
|
console.log(`[handleSaveLine] workspaceThresholdUpdates for ${lineId}:`, workspaceThresholdUpdates);
|
|
33209
33173
|
await workspaceService.updateActionThresholds(workspaceThresholdUpdates);
|
|
33210
33174
|
console.log(`[handleSaveLine] Successfully updated action thresholds for ${lineId}`);
|
|
33175
|
+
const packagingWorkspaces = lineDataToSave.workspaces.filter((ws) => ws.actionType === "packaging");
|
|
33211
33176
|
const lineThresholdData = {
|
|
33212
33177
|
factory_id: currentFactoryId,
|
|
33213
33178
|
line_id: lineId,
|
|
33214
33179
|
date: currentDate,
|
|
33215
33180
|
shift_id: selectedShift,
|
|
33216
33181
|
product_code: lineDataToSave.productId,
|
|
33217
|
-
threshold_day_output:
|
|
33218
|
-
threshold_pph:
|
|
33182
|
+
threshold_day_output: packagingWorkspaces.reduce((acc, ws) => acc + (Number(ws.targetDayOutput) || 0), 0),
|
|
33183
|
+
threshold_pph: packagingWorkspaces.reduce((acc, ws) => acc + (Number(ws.targetPPH) || 0), 0),
|
|
33219
33184
|
...skuEnabled && lineDataToSave.selectedSKU ? { sku_id: lineDataToSave.selectedSKU.id } : {}
|
|
33220
33185
|
};
|
|
33221
33186
|
console.log(`[handleSaveLine] lineThresholdData for upsert on ${lineId}:`, lineThresholdData);
|
|
@@ -33226,20 +33191,6 @@ var TargetsView = ({
|
|
|
33226
33191
|
throw lineUpsertError;
|
|
33227
33192
|
}
|
|
33228
33193
|
console.log(`[handleSaveLine] Successfully upserted line_thresholds for ${lineId}`);
|
|
33229
|
-
const operatingHoursData = {
|
|
33230
|
-
line_id: lineId,
|
|
33231
|
-
shift_id: selectedShift,
|
|
33232
|
-
start_time: lineDataToSave.shiftStartTime,
|
|
33233
|
-
end_time: lineDataToSave.shiftEndTime,
|
|
33234
|
-
breaks: lineDataToSave.breaks
|
|
33235
|
-
};
|
|
33236
|
-
console.log(`[handleSaveLine] operatingHoursData for upsert on ${lineId}:`, operatingHoursData);
|
|
33237
|
-
const { error: operatingHoursError } = await supabase.from("line_operating_hours").upsert(operatingHoursData, { onConflict: "line_id,shift_id" });
|
|
33238
|
-
if (operatingHoursError) {
|
|
33239
|
-
console.error(`[handleSaveLine] Error upserting line_operating_hours for ${lineId}:`, operatingHoursError);
|
|
33240
|
-
sonner.toast.error(`Failed to update shift hours for ${lineNames[lineId] || lineId}`);
|
|
33241
|
-
}
|
|
33242
|
-
console.log(`[handleSaveLine] Successfully upserted line_operating_hours for ${lineId}`);
|
|
33243
33194
|
setSaveSuccess((prev) => ({ ...prev, [lineId]: true }));
|
|
33244
33195
|
sonner.toast.success(`${lineNames[lineId] || lineId} targets saved successfully`);
|
|
33245
33196
|
if (onSaveChanges) onSaveChanges(lineId);
|
|
@@ -33284,19 +33235,6 @@ var TargetsView = ({
|
|
|
33284
33235
|
})
|
|
33285
33236
|
}
|
|
33286
33237
|
}));
|
|
33287
|
-
try {
|
|
33288
|
-
const line = lineWorkspaces[updates.lineId];
|
|
33289
|
-
const currentHours = await loadOperatingHours(updates.lineId, selectedShift);
|
|
33290
|
-
await supabase?.from("line_operating_hours").upsert({
|
|
33291
|
-
line_id: updates.lineId,
|
|
33292
|
-
shift_id: selectedShift,
|
|
33293
|
-
start_time: line.shiftStartTime,
|
|
33294
|
-
end_time: line.shiftEndTime,
|
|
33295
|
-
breaks: currentHours?.breaks || line.breaks || []
|
|
33296
|
-
});
|
|
33297
|
-
} catch (error) {
|
|
33298
|
-
console.error("Error updating line operating hours:", error);
|
|
33299
|
-
}
|
|
33300
33238
|
sonner.toast.success(`Updated ${updates.workspaceIds.length} workspaces in ${lineNames[updates.lineId] || updates.lineId}`);
|
|
33301
33239
|
setIsBulkConfigureOpen(false);
|
|
33302
33240
|
};
|
package/dist/index.mjs
CHANGED
|
@@ -32562,69 +32562,119 @@ var TargetsView = ({
|
|
|
32562
32562
|
const { skus, isLoading: skusLoading } = useSKUs(companyId);
|
|
32563
32563
|
const skuEnabled = dashboardConfig?.skuConfig?.enabled || false;
|
|
32564
32564
|
useEffect(() => {
|
|
32565
|
-
|
|
32565
|
+
let timeoutId;
|
|
32566
|
+
let retryCount = 0;
|
|
32567
|
+
const MAX_RETRIES2 = 2;
|
|
32568
|
+
const LOADING_TIMEOUT = 15e3;
|
|
32569
|
+
const fetchInitialData = async () => {
|
|
32566
32570
|
if (!supabase || lineIds.length === 0) return;
|
|
32567
|
-
|
|
32568
|
-
|
|
32569
|
-
|
|
32570
|
-
|
|
32571
|
-
|
|
32572
|
-
|
|
32573
|
-
|
|
32574
|
-
|
|
32575
|
-
}
|
|
32576
|
-
|
|
32577
|
-
|
|
32571
|
+
setIsLoading(true);
|
|
32572
|
+
timeoutId = setTimeout(() => {
|
|
32573
|
+
console.error("Loading timeout reached");
|
|
32574
|
+
if (retryCount < MAX_RETRIES2) {
|
|
32575
|
+
retryCount++;
|
|
32576
|
+
console.log(`Retrying... (attempt ${retryCount + 1}/${MAX_RETRIES2 + 1})`);
|
|
32577
|
+
toast.warning("Loading is taking longer than expected. Retrying...");
|
|
32578
|
+
fetchInitialData();
|
|
32579
|
+
} else {
|
|
32580
|
+
setIsLoading(false);
|
|
32581
|
+
toast.error("Failed to load data. Please refresh the page.");
|
|
32578
32582
|
}
|
|
32579
|
-
});
|
|
32580
|
-
const results = await Promise.all(detailsPromises);
|
|
32581
|
-
setLineWorkspaces((prev) => {
|
|
32582
|
-
const newWorkspaces = { ...prev };
|
|
32583
|
-
let needsUpdate = false;
|
|
32584
|
-
results.forEach((result) => {
|
|
32585
|
-
if (result.factoryId && newWorkspaces[result.lineId] && newWorkspaces[result.lineId].factoryId !== result.factoryId) {
|
|
32586
|
-
newWorkspaces[result.lineId].factoryId = result.factoryId;
|
|
32587
|
-
needsUpdate = true;
|
|
32588
|
-
}
|
|
32589
|
-
});
|
|
32590
|
-
return needsUpdate ? newWorkspaces : prev;
|
|
32591
|
-
});
|
|
32592
|
-
};
|
|
32593
|
-
fetchLineDetails();
|
|
32594
|
-
}, [supabase, lineIds]);
|
|
32595
|
-
useEffect(() => {
|
|
32596
|
-
const fetchActions = async () => {
|
|
32597
|
-
if (!supabase) {
|
|
32598
|
-
console.error("Supabase client not available in fetchActions");
|
|
32599
|
-
toast.error("Initialization error, please refresh.");
|
|
32600
|
-
return;
|
|
32601
|
-
}
|
|
32583
|
+
}, LOADING_TIMEOUT);
|
|
32602
32584
|
try {
|
|
32603
|
-
const actions = await
|
|
32604
|
-
|
|
32605
|
-
|
|
32606
|
-
|
|
32585
|
+
const [factoryResults, actions] = await Promise.all([
|
|
32586
|
+
// Fetch factory IDs
|
|
32587
|
+
Promise.all(lineIds.map(async (lineId) => {
|
|
32588
|
+
try {
|
|
32589
|
+
const { data, error } = await supabase.from("lines").select("factory_id").eq("id", lineId).single();
|
|
32590
|
+
if (error) {
|
|
32591
|
+
console.error(`Error fetching factory_id for line ${lineId}:`, error);
|
|
32592
|
+
return { lineId, factoryId: void 0 };
|
|
32593
|
+
}
|
|
32594
|
+
return { lineId, factoryId: data?.factory_id };
|
|
32595
|
+
} catch (err) {
|
|
32596
|
+
console.error(`Exception fetching factory_id for line ${lineId}:`, err);
|
|
32597
|
+
return { lineId, factoryId: void 0 };
|
|
32598
|
+
}
|
|
32599
|
+
})),
|
|
32600
|
+
// Fetch action IDs
|
|
32601
|
+
actionService.getActionsByName(
|
|
32602
|
+
[ACTION_NAMES.ASSEMBLY, ACTION_NAMES.PACKAGING],
|
|
32603
|
+
companyId
|
|
32604
|
+
)
|
|
32605
|
+
]);
|
|
32607
32606
|
const assemblyAction = actions.find((a) => a.action_name === ACTION_NAMES.ASSEMBLY);
|
|
32608
32607
|
const packagingAction = actions.find((a) => a.action_name === ACTION_NAMES.PACKAGING);
|
|
32609
32608
|
if (!assemblyAction || !packagingAction) {
|
|
32610
32609
|
throw new Error("Could not find required actions");
|
|
32611
32610
|
}
|
|
32612
|
-
const
|
|
32611
|
+
const actionIdsData = {
|
|
32613
32612
|
assembly: assemblyAction.id,
|
|
32614
32613
|
packaging: packagingAction.id
|
|
32615
32614
|
};
|
|
32616
|
-
|
|
32617
|
-
|
|
32618
|
-
|
|
32615
|
+
setActionIds(actionIdsData);
|
|
32616
|
+
const updatedLineWorkspaces = { ...initialLineWorkspaces };
|
|
32617
|
+
factoryResults.forEach((result) => {
|
|
32618
|
+
if (result.factoryId && updatedLineWorkspaces[result.lineId]) {
|
|
32619
|
+
updatedLineWorkspaces[result.lineId].factoryId = result.factoryId;
|
|
32620
|
+
}
|
|
32619
32621
|
});
|
|
32620
|
-
|
|
32622
|
+
const currentDate = getOperationalDate();
|
|
32623
|
+
for (const lineId of lineIds) {
|
|
32624
|
+
if (!updatedLineWorkspaces[lineId]?.factoryId) {
|
|
32625
|
+
console.warn(`Skipping workspace fetch for line ${lineId} - no factory ID`);
|
|
32626
|
+
continue;
|
|
32627
|
+
}
|
|
32628
|
+
try {
|
|
32629
|
+
const workspacesData = await workspaceService.getWorkspaces(lineId);
|
|
32630
|
+
const actionThresholds = await workspaceService.getActionThresholds(
|
|
32631
|
+
lineId,
|
|
32632
|
+
currentDate,
|
|
32633
|
+
selectedShift
|
|
32634
|
+
);
|
|
32635
|
+
const mappedWorkspaces = workspacesData.map((ws) => {
|
|
32636
|
+
const threshold = actionThresholds.find((t) => t.workspace_id === ws.id);
|
|
32637
|
+
return {
|
|
32638
|
+
id: ws.id,
|
|
32639
|
+
name: ws.workspace_id,
|
|
32640
|
+
targetPPH: threshold?.pph_threshold ?? (ws.action_pph_threshold === null ? "" : ws.action_pph_threshold),
|
|
32641
|
+
targetCycleTime: threshold?.ideal_cycle_time ?? (ws.action_cycle_time === null ? "" : ws.action_cycle_time),
|
|
32642
|
+
targetDayOutput: threshold?.total_day_output ?? (ws.action_total_day_output === null ? "" : ws.action_total_day_output),
|
|
32643
|
+
actionType: ws.action_id === actionIdsData.assembly ? "assembly" : ws.action_id === actionIdsData.packaging ? "packaging" : "assembly",
|
|
32644
|
+
actionId: ws.action_id === actionIdsData.assembly ? actionIdsData.assembly : ws.action_id === actionIdsData.packaging ? actionIdsData.packaging : actionIdsData.assembly
|
|
32645
|
+
};
|
|
32646
|
+
}).sort((a, b) => a.name.localeCompare(b.name, void 0, { numeric: true }));
|
|
32647
|
+
updatedLineWorkspaces[lineId].workspaces = mappedWorkspaces;
|
|
32648
|
+
} catch (error) {
|
|
32649
|
+
console.error(`Error fetching workspace data for line ${lineId}:`, error);
|
|
32650
|
+
}
|
|
32651
|
+
}
|
|
32652
|
+
setLineWorkspaces(updatedLineWorkspaces);
|
|
32653
|
+
await fetchAllShiftsData(updatedLineWorkspaces);
|
|
32621
32654
|
} catch (error) {
|
|
32622
|
-
console.error("Error fetching
|
|
32623
|
-
|
|
32655
|
+
console.error("Error fetching initial data:", error);
|
|
32656
|
+
clearTimeout(timeoutId);
|
|
32657
|
+
if (retryCount < MAX_RETRIES2) {
|
|
32658
|
+
retryCount++;
|
|
32659
|
+
console.log(`Error occurred, retrying... (attempt ${retryCount + 1}/${MAX_RETRIES2 + 1})`);
|
|
32660
|
+
toast.warning("Error loading data. Retrying...");
|
|
32661
|
+
setTimeout(() => fetchInitialData(), 1e3);
|
|
32662
|
+
} else {
|
|
32663
|
+
toast.error("Failed to load initial data");
|
|
32664
|
+
setIsLoading(false);
|
|
32665
|
+
}
|
|
32666
|
+
} finally {
|
|
32667
|
+
clearTimeout(timeoutId);
|
|
32668
|
+
if (retryCount === 0 || retryCount >= MAX_RETRIES2) {
|
|
32669
|
+
setIsLoading(false);
|
|
32670
|
+
}
|
|
32624
32671
|
}
|
|
32625
32672
|
};
|
|
32626
|
-
|
|
32627
|
-
|
|
32673
|
+
fetchInitialData();
|
|
32674
|
+
return () => {
|
|
32675
|
+
clearTimeout(timeoutId);
|
|
32676
|
+
};
|
|
32677
|
+
}, [supabase, lineIds, companyId]);
|
|
32628
32678
|
useCallback(async (shiftId) => {
|
|
32629
32679
|
try {
|
|
32630
32680
|
if (!supabase) return;
|
|
@@ -32867,92 +32917,6 @@ var TargetsView = ({
|
|
|
32867
32917
|
};
|
|
32868
32918
|
}
|
|
32869
32919
|
}, [supabase]);
|
|
32870
|
-
useEffect(() => {
|
|
32871
|
-
const allFactoryIdsLoaded = lineIds.every((lineId) => lineWorkspaces[lineId]?.factoryId);
|
|
32872
|
-
if (!actionIds || !allFactoryIdsLoaded) {
|
|
32873
|
-
return;
|
|
32874
|
-
}
|
|
32875
|
-
const workspacesAlreadyLoadedForAnyLine = Object.values(lineWorkspaces).some(
|
|
32876
|
-
(line) => line.workspaces && line.workspaces.length > 0
|
|
32877
|
-
);
|
|
32878
|
-
if (workspacesAlreadyLoadedForAnyLine) {
|
|
32879
|
-
setIsLoading(false);
|
|
32880
|
-
return;
|
|
32881
|
-
}
|
|
32882
|
-
const fetchWorkspacesAndThenThresholds = async () => {
|
|
32883
|
-
setIsLoading(true);
|
|
32884
|
-
try {
|
|
32885
|
-
if (!supabase) {
|
|
32886
|
-
toast.error("Supabase client not available");
|
|
32887
|
-
setIsLoading(false);
|
|
32888
|
-
return;
|
|
32889
|
-
}
|
|
32890
|
-
console.log("Starting workspace fetch with actionIds and loaded factoryIds.");
|
|
32891
|
-
const newUpdatedLineWorkspaces = { ...lineWorkspaces };
|
|
32892
|
-
let workspacesHaveBeenUpdated = false;
|
|
32893
|
-
for (const lineId of lineIds) {
|
|
32894
|
-
if (!newUpdatedLineWorkspaces[lineId]?.factoryId) {
|
|
32895
|
-
console.warn(`FactoryId for line ${lineId} missing during workspace fetch. Skipping its workspaces.`);
|
|
32896
|
-
continue;
|
|
32897
|
-
}
|
|
32898
|
-
try {
|
|
32899
|
-
const fetchedLineWorkspacesData = await workspaceService.getWorkspaces(lineId);
|
|
32900
|
-
let mappedWorkspaces = fetchedLineWorkspacesData.map((ws) => ({
|
|
32901
|
-
id: ws.id,
|
|
32902
|
-
name: ws.workspace_id,
|
|
32903
|
-
targetPPH: ws.action_pph_threshold === null ? "" : ws.action_pph_threshold,
|
|
32904
|
-
targetCycleTime: ws.action_cycle_time === null ? "" : ws.action_cycle_time,
|
|
32905
|
-
targetDayOutput: ws.action_total_day_output === null ? "" : ws.action_total_day_output,
|
|
32906
|
-
actionType: ws.action_id === actionIds.assembly ? "assembly" : ws.action_id === actionIds.packaging ? "packaging" : "assembly",
|
|
32907
|
-
actionId: ws.action_id === actionIds.assembly ? actionIds.assembly : ws.action_id === actionIds.packaging ? actionIds.packaging : actionIds.assembly
|
|
32908
|
-
})).sort((a, b) => a.name.localeCompare(b.name, void 0, { numeric: true }));
|
|
32909
|
-
const currentDate = getOperationalDate();
|
|
32910
|
-
try {
|
|
32911
|
-
const actionThresholds = await workspaceService.getActionThresholds(
|
|
32912
|
-
lineId,
|
|
32913
|
-
currentDate,
|
|
32914
|
-
selectedShift
|
|
32915
|
-
);
|
|
32916
|
-
mappedWorkspaces = mappedWorkspaces.map((ws) => {
|
|
32917
|
-
const threshold = actionThresholds.find((t) => t.workspace_id === ws.id);
|
|
32918
|
-
if (threshold) {
|
|
32919
|
-
return {
|
|
32920
|
-
...ws,
|
|
32921
|
-
targetPPH: threshold.pph_threshold,
|
|
32922
|
-
targetCycleTime: threshold.ideal_cycle_time,
|
|
32923
|
-
targetDayOutput: threshold.total_day_output
|
|
32924
|
-
};
|
|
32925
|
-
}
|
|
32926
|
-
return ws;
|
|
32927
|
-
});
|
|
32928
|
-
console.log(`Merged action thresholds for line ${lineId}, found ${actionThresholds.length} saved thresholds`);
|
|
32929
|
-
} catch (error) {
|
|
32930
|
-
console.error(`Error fetching action thresholds for line ${lineId}:`, error);
|
|
32931
|
-
}
|
|
32932
|
-
if (JSON.stringify(mappedWorkspaces) !== JSON.stringify(newUpdatedLineWorkspaces[lineId].workspaces)) {
|
|
32933
|
-
newUpdatedLineWorkspaces[lineId] = {
|
|
32934
|
-
...newUpdatedLineWorkspaces[lineId],
|
|
32935
|
-
workspaces: mappedWorkspaces
|
|
32936
|
-
};
|
|
32937
|
-
workspacesHaveBeenUpdated = true;
|
|
32938
|
-
}
|
|
32939
|
-
} catch (error) {
|
|
32940
|
-
console.error(`Error fetching workspaces for line ${lineId}:`, error);
|
|
32941
|
-
}
|
|
32942
|
-
}
|
|
32943
|
-
if (workspacesHaveBeenUpdated) {
|
|
32944
|
-
setLineWorkspaces(newUpdatedLineWorkspaces);
|
|
32945
|
-
}
|
|
32946
|
-
await fetchAllShiftsData(newUpdatedLineWorkspaces);
|
|
32947
|
-
} catch (error) {
|
|
32948
|
-
console.error("Error in fetchWorkspacesAndThenThresholds:", error);
|
|
32949
|
-
toast.error("Failed to load workspace data");
|
|
32950
|
-
} finally {
|
|
32951
|
-
setIsLoading(false);
|
|
32952
|
-
}
|
|
32953
|
-
};
|
|
32954
|
-
fetchWorkspacesAndThenThresholds();
|
|
32955
|
-
}, [actionIds, supabase, lineIds]);
|
|
32956
32920
|
const toggleLineDropdown = useCallback((lineId) => {
|
|
32957
32921
|
setLineWorkspaces((prev) => {
|
|
32958
32922
|
const newIsOpen = !prev[lineId].isOpen;
|
|
@@ -33179,14 +33143,15 @@ var TargetsView = ({
|
|
|
33179
33143
|
console.log(`[handleSaveLine] workspaceThresholdUpdates for ${lineId}:`, workspaceThresholdUpdates);
|
|
33180
33144
|
await workspaceService.updateActionThresholds(workspaceThresholdUpdates);
|
|
33181
33145
|
console.log(`[handleSaveLine] Successfully updated action thresholds for ${lineId}`);
|
|
33146
|
+
const packagingWorkspaces = lineDataToSave.workspaces.filter((ws) => ws.actionType === "packaging");
|
|
33182
33147
|
const lineThresholdData = {
|
|
33183
33148
|
factory_id: currentFactoryId,
|
|
33184
33149
|
line_id: lineId,
|
|
33185
33150
|
date: currentDate,
|
|
33186
33151
|
shift_id: selectedShift,
|
|
33187
33152
|
product_code: lineDataToSave.productId,
|
|
33188
|
-
threshold_day_output:
|
|
33189
|
-
threshold_pph:
|
|
33153
|
+
threshold_day_output: packagingWorkspaces.reduce((acc, ws) => acc + (Number(ws.targetDayOutput) || 0), 0),
|
|
33154
|
+
threshold_pph: packagingWorkspaces.reduce((acc, ws) => acc + (Number(ws.targetPPH) || 0), 0),
|
|
33190
33155
|
...skuEnabled && lineDataToSave.selectedSKU ? { sku_id: lineDataToSave.selectedSKU.id } : {}
|
|
33191
33156
|
};
|
|
33192
33157
|
console.log(`[handleSaveLine] lineThresholdData for upsert on ${lineId}:`, lineThresholdData);
|
|
@@ -33197,20 +33162,6 @@ var TargetsView = ({
|
|
|
33197
33162
|
throw lineUpsertError;
|
|
33198
33163
|
}
|
|
33199
33164
|
console.log(`[handleSaveLine] Successfully upserted line_thresholds for ${lineId}`);
|
|
33200
|
-
const operatingHoursData = {
|
|
33201
|
-
line_id: lineId,
|
|
33202
|
-
shift_id: selectedShift,
|
|
33203
|
-
start_time: lineDataToSave.shiftStartTime,
|
|
33204
|
-
end_time: lineDataToSave.shiftEndTime,
|
|
33205
|
-
breaks: lineDataToSave.breaks
|
|
33206
|
-
};
|
|
33207
|
-
console.log(`[handleSaveLine] operatingHoursData for upsert on ${lineId}:`, operatingHoursData);
|
|
33208
|
-
const { error: operatingHoursError } = await supabase.from("line_operating_hours").upsert(operatingHoursData, { onConflict: "line_id,shift_id" });
|
|
33209
|
-
if (operatingHoursError) {
|
|
33210
|
-
console.error(`[handleSaveLine] Error upserting line_operating_hours for ${lineId}:`, operatingHoursError);
|
|
33211
|
-
toast.error(`Failed to update shift hours for ${lineNames[lineId] || lineId}`);
|
|
33212
|
-
}
|
|
33213
|
-
console.log(`[handleSaveLine] Successfully upserted line_operating_hours for ${lineId}`);
|
|
33214
33165
|
setSaveSuccess((prev) => ({ ...prev, [lineId]: true }));
|
|
33215
33166
|
toast.success(`${lineNames[lineId] || lineId} targets saved successfully`);
|
|
33216
33167
|
if (onSaveChanges) onSaveChanges(lineId);
|
|
@@ -33255,19 +33206,6 @@ var TargetsView = ({
|
|
|
33255
33206
|
})
|
|
33256
33207
|
}
|
|
33257
33208
|
}));
|
|
33258
|
-
try {
|
|
33259
|
-
const line = lineWorkspaces[updates.lineId];
|
|
33260
|
-
const currentHours = await loadOperatingHours(updates.lineId, selectedShift);
|
|
33261
|
-
await supabase?.from("line_operating_hours").upsert({
|
|
33262
|
-
line_id: updates.lineId,
|
|
33263
|
-
shift_id: selectedShift,
|
|
33264
|
-
start_time: line.shiftStartTime,
|
|
33265
|
-
end_time: line.shiftEndTime,
|
|
33266
|
-
breaks: currentHours?.breaks || line.breaks || []
|
|
33267
|
-
});
|
|
33268
|
-
} catch (error) {
|
|
33269
|
-
console.error("Error updating line operating hours:", error);
|
|
33270
|
-
}
|
|
33271
33209
|
toast.success(`Updated ${updates.workspaceIds.length} workspaces in ${lineNames[updates.lineId] || updates.lineId}`);
|
|
33272
33210
|
setIsBulkConfigureOpen(false);
|
|
33273
33211
|
};
|