6 Commits

Author SHA1 Message Date
8fc3129f7d refactor(opend dock): added in default dock so it uses the default setup as a backup
All checks were successful
Build and Push LST Docker Image / docker (push) Successful in 1m40s
This will help the live/drop and dont know what dock
2026-06-09 12:00:50 -05:00
05c553e927 fix(eom): removed un needed imports 2026-06-09 11:59:48 -05:00
6eaae0f537 refactor(dock scanner): more work on dock scanner and semi finished 2026-06-09 11:59:27 -05:00
3ad84dab71 refactor(opendock): added in proper complete and ignore of picksheets 2026-06-09 11:58:25 -05:00
5a7046bacd refactor(opendock): if load type is drop we will not do anything unless its already scanned
this means that if we drag down a bunch of loads we wont instantly change to arrived we will need to
have a single scan before we do this
2026-06-09 11:46:22 -05:00
cfc497c1f2 refactor(opendock): added in check for really using the article link 2026-06-09 11:45:09 -05:00
18 changed files with 3301 additions and 171 deletions

View File

@@ -6,7 +6,7 @@ export const dockDoorScans = pgTable("dock_door_scans", {
id: uuid("id").defaultRandom().primaryKey(), id: uuid("id").defaultRandom().primaryKey(),
dockId: text("dock_id").notNull(), dockId: text("dock_id").notNull(),
loadingOrder: text("loading_order").notNull(), loadingOrder: text("loading_order").notNull(),
loadingUnit: text("loading_Unit").unique(), // can be running number or sscc depending on where it came from loadingUnit: text("loading_Unit"), // can be running number or sscc depending on where it came from
loadingUnitStatus: text("loading_unit_status").default("loaded"), // TODO: add enums on the status of each load. loadingUnitStatus: text("loading_unit_status").default("loaded"), // TODO: add enums on the status of each load.
message: text("message"), // the response it gave when scanning message: text("message"), // the response it gave when scanning
status: text("status").default("active"), // TODO: add in enums for this status: text("status").default("active"), // TODO: add in enums for this

View File

@@ -16,6 +16,7 @@ r.get("/", async (_, res) => {
loadingDateTo: format(addDays(new Date(Date.now()), 3), "yyyy-MM-dd"), loadingDateTo: format(addDays(new Date(Date.now()), 3), "yyyy-MM-dd"),
states: [ states: [
1, // planned 1, // planned
2, // loading
], ],
//isCommissioned: true, //isCommissioned: true,
}, },

View File

@@ -32,13 +32,34 @@ r.post("/", async (req, res) => {
})) as any; })) as any;
if (orders?.data.errors) { if (orders?.data.errors) {
console.log(orders.data.errors); //console.log(orders.data.errors);
// if (orders.data.errors[0].code === 20) {
// await db
// .update(dockDoorScanners)
// .set({
// currentLoadingOrder: "",
// upd_date: sql`NOW()`,
// upd_user: req.user?.username ?? "lst-dock-system",
// })
// .where(eq(dockDoorScanners.dockId, validated.dockId));
// return apiReturn(res, {
// success: false,
// level: "warn",
// module: "dockdoor",
// subModule: "loadingOrder",
// message: `Loading order: ${validated.loadingOrder} cleared, It was probable completed by a scanner.. or user...`,
// data: (orders.data.errors as any) ?? [],
// status: 200,
// });
// }
return apiReturn(res, { return apiReturn(res, {
success: false, success: false,
level: "error", level: "error",
module: "dockdoor", module: "dockdoor",
subModule: "loadingOrder", subModule: "loadingOrder",
message: `Failed to finish the order.`, message: `Failed to finish the order: ${orders.data.errors[0].message}`,
data: (orders.data.errors as any) ?? [], data: (orders.data.errors as any) ?? [],
status: 400, status: 400,
}); });
@@ -48,6 +69,7 @@ r.post("/", async (req, res) => {
db db
.update(dockDoorScans) .update(dockDoorScans)
.set({ .set({
status: "completed",
upd_date: sql`NOW()`, upd_date: sql`NOW()`,
upd_user: req.user?.username ?? "lst-dock-system", upd_user: req.user?.username ?? "lst-dock-system",
}) })

View File

@@ -19,13 +19,18 @@ type Data = {
const postScan = async (data: any) => { const postScan = async (data: any) => {
try { try {
await db.insert(dockDoorScans).values({ const newScan = (await db
dockId: data.dockId, .insert(dockDoorScans)
loadingOrder: data.loadingOrder, .values({
loadingUnit: data.loadingUnit.sscc ?? data.loadingUnit.runningNo, // can be running number or sscc depending on where it came from dockId: data.dockId,
loadingUnitStatus: data.loadingUnitStatus, // TODO: add enums on the status of each load. loadingOrder: data.loadingOrder,
message: data.message, // the response it gave when scanning loadingUnit: data.loadingUnit.sscc ?? data.loadingUnit.runningNo, // can be running number or sscc depending on where it came from
}); loadingUnitStatus: data.loadingUnitStatus, // TODO: add enums on the status of each load.
message: data.message, // the response it gave when scanning
})
.returning()) as any;
emitToRoom(`dockDoorLoading:${data.dockId}`, newScan[0]);
} catch (error) { } catch (error) {
console.log("Error: ", error); console.log("Error: ", error);
} }
@@ -133,7 +138,7 @@ const loadUnit = async (data: Data) => {
loadingUnitStatus: "notLoaded", loadingUnitStatus: "notLoaded",
message: prod?.data.errors[0].message, message: prod?.data.errors[0].message,
}); });
emitToRoom(`dockDoorLoading:${data.dockId}`, prod?.data.errors[0]);
return returnFunc({ return returnFunc({
success: false, success: false,
level: "error", level: "error",
@@ -158,7 +163,7 @@ const loadUnit = async (data: Data) => {
loadingUnitStatus: "loaded", loadingUnitStatus: "loaded",
message: emitData.message, message: emitData.message,
}); });
emitToRoom(`dockDoorLoading:${data.dockId}`, emitData as any);
return returnFunc({ return returnFunc({
success: true, success: true,
level: "info", level: "info",

View File

@@ -1,4 +1,3 @@
import { formatInTimeZone } from "date-fns-tz";
import { Router } from "express"; import { Router } from "express";
import { prodQuery } from "../prodSql/prodSqlQuery.controller.js"; import { prodQuery } from "../prodSql/prodSqlQuery.controller.js";
import { import {

View File

@@ -1,4 +1,3 @@
import { formatInTimeZone } from "date-fns-tz";
import { Router } from "express"; import { Router } from "express";
import { prodQuery } from "../prodSql/prodSqlQuery.controller.js"; import { prodQuery } from "../prodSql/prodSqlQuery.controller.js";
import { import {

View File

@@ -277,7 +277,7 @@ const postRelease = async (release: Releases) => {
(releaseLoadtypeCheck || (releaseLoadtypeCheck ||
opendDockArticleCheck?.loadType === "drop" || opendDockArticleCheck?.loadType === "drop" ||
defaultDock?.value === "drop") && defaultDock?.value === "drop") &&
(release.DeliveryState === 0 || release.DeliveryState === 1) (release.DeliveryState === 0 || release.DeliveryState === 2)
) { ) {
const setArrival = { ...newDockApt, status: "Arrived" }; const setArrival = { ...newDockApt, status: "Arrived" };
@@ -391,7 +391,8 @@ const postRelease = async (release: Releases) => {
return; return;
} }
} else { // changing to only trigger the change if the state is 2 meaning it has a scan to it and already in progress of being loaded.
} else if (release.DeliveryState === 0 || release.DeliveryState === 2) {
try { try {
const response = await axios.patch( const response = await axios.patch(
`${process.env.OPENDOCK_URL}/appointment/${id}`, `${process.env.OPENDOCK_URL}/appointment/${id}`,
@@ -445,6 +446,116 @@ const postRelease = async (release: Releases) => {
return; return;
} }
// if we are finished we need to set to completed
} else if (release.DeliveryState === 3 || release.DeliveryState === 4) {
try {
const response = await axios.patch(
`${process.env.OPENDOCK_URL}/appointment/${id}`,
newDockApt,
{
headers: {
"content-type": "application/json; charset=utf-8",
Authorization: `Bearer ${odToken.odToken}`,
},
},
);
if (response.status === 400) {
log.error({}, response.data.data.message);
return;
}
// update the release in the db leaving as insert just incase something weird happened
try {
await db
.insert(opendockApt)
.values({
release: release.ReleaseNumber,
openDockAptId: response.data.data.id,
appointment: response.data.data,
})
.onConflictDoUpdate({
target: opendockApt.release,
set: {
openDockAptId: response.data.data.id,
appointment: response.data.data,
upd_date: sql`NOW()`,
},
})
.returning();
log.info({}, `${release.ReleaseNumber} was updated`);
} catch (e) {
log.error(
{ stack: e },
`Error updating the release: ${release.ReleaseNumber}`,
);
}
// biome-ignore lint/suspicious/noExplicitAny: to many possibilities
} catch (e: any) {
//console.info(newDockApt);
log.error(
{ stack: e.response.data },
`An error has occurred during patching of the release: ${release.ReleaseNumber}`,
);
return;
}
}
} else if (opendDockArticleCheck?.loadType === "live") {
try {
const response = await axios.post(
`${process.env.OPENDOCK_URL}/appointment`,
newDockApt,
{
headers: {
"content-type": "application/json; charset=utf-8",
Authorization: `Bearer ${odToken.odToken}`,
},
},
);
// we need the id,release#,status from this response, store it in lst, check if we have a release so we can just update it.
// this will be utilized when we are listening for the changes to the apts. that way we can update the state to arrived. we will run our own checks on this guy during the incoming messages.
if (response.status === 400) {
log.error({}, response.data.data.message);
return;
}
// the response to make it simple we want response.data.id, response.data.relNumber, status will be defaulted to Scheduled if we created it here.
// TODO: add this release data to our db. but save it in json format and well parse it out. that way we future proof it and have everything in here vs just a few things
//console.info(response.data.data, "Was Created");
try {
await db
.insert(opendockApt)
.values({
release: release.ReleaseNumber,
openDockAptId: response.data.data.id,
appointment: response.data.data,
})
.onConflictDoUpdate({
target: opendockApt.release,
set: {
openDockAptId: response.data.data.id,
appointment: response.data.data,
upd_date: sql`NOW()`,
},
})
.returning();
log.info({}, `${release.ReleaseNumber} was created`);
} catch (e) {
log.error({ stack: e }, "Error creating new release");
}
// biome-ignore lint/suspicious/noExplicitAny: to many possibilities
} catch (e: any) {
log.error(
{ stack: e?.response?.data },
`Error posting new release to opendock, ${release.ReleaseNumber}`,
);
return;
} }
} else if ( } else if (
(releaseLoadtypeCheck || (releaseLoadtypeCheck ||

View File

@@ -1,8 +1,8 @@
import { desc, eq } from "drizzle-orm"; import { desc, eq } from "drizzle-orm";
import { db } from "../db/db.controller.js"; import { db } from "../db/db.controller.js";
import { dockDoorScans } from "../db/schema/dockdoor.scans.schema.js";
import { logs } from "../db/schema/logs.schema.js"; import { logs } from "../db/schema/logs.schema.js";
import { ppoRun } from "../warehousing/warehousing.ppooMonitor.js"; import { ppoRun } from "../warehousing/warehousing.ppooMonitor.js";
import { dockDoorScans } from "../db/schema/dockdoor.scans.schema.js";
type RoomDefinition<T = unknown> = { type RoomDefinition<T = unknown> = {
seed: (limit: number) => Promise<T[]>; seed: (limit: number) => Promise<T[]>;
@@ -104,10 +104,12 @@ export const roomDefinition: Record<RoomId, RoomDefinition> = {
"dockDoorLoading:2": { "dockDoorLoading:2": {
seed: async (limit) => { seed: async (limit) => {
console.log(limit); console.log(limit);
console.log("reseeiding");
try { try {
const rows = await db const rows = await db
.select() .select()
.from(dockDoorScans).where(eq(dockDoorScans.status, "active")) .from(dockDoorScans)
.where(eq(dockDoorScans.status, "active"))
.orderBy(desc(dockDoorScans.upd_date)) .orderBy(desc(dockDoorScans.upd_date))
.limit(limit); .limit(limit);

View File

@@ -30,7 +30,7 @@ export function useSocketRoom<T>(
setInfo(`Removed item ${id}`); setInfo(`Removed item ${id}`);
return; return;
} }
console.log("cleared data from the room");
setData([]); setData([]);
setInfo("Room data cleared"); setInfo("Room data cleared");
}, },

View File

@@ -24,11 +24,11 @@ import { Route as AdminLogsRouteImport } from './routes/admin/logs'
import { Route as authLoginRouteImport } from './routes/(auth)/login' import { Route as authLoginRouteImport } from './routes/(auth)/login'
import { Route as WarehouseDockdoorscanningIndexRouteImport } from './routes/warehouse/dockdoorscanning/index' import { Route as WarehouseDockdoorscanningIndexRouteImport } from './routes/warehouse/dockdoorscanning/index'
import { Route as TransportationOpendockIndexRouteImport } from './routes/transportation/opendock/index' import { Route as TransportationOpendockIndexRouteImport } from './routes/transportation/opendock/index'
import { Route as WarehouseDockdoorscanningDockScansRouteImport } from './routes/warehouse/dockdoorscanning/$dockScans'
import { Route as WarehouseDockdoorscanningDockRouteImport } from './routes/warehouse/dockdoorscanning/$dock' import { Route as WarehouseDockdoorscanningDockRouteImport } from './routes/warehouse/dockdoorscanning/$dock'
import { Route as authUserSignupRouteImport } from './routes/(auth)/user.signup' import { Route as authUserSignupRouteImport } from './routes/(auth)/user.signup'
import { Route as authUserResetpasswordRouteImport } from './routes/(auth)/user.resetpassword' import { Route as authUserResetpasswordRouteImport } from './routes/(auth)/user.resetpassword'
import { Route as authUserProfileRouteImport } from './routes/(auth)/user.profile' import { Route as authUserProfileRouteImport } from './routes/(auth)/user.profile'
import { Route as WarehouseDockdoorscanningScansDockScansRouteImport } from './routes/warehouse/dockdoorscanning/scans/$dockScans'
const ForbiddenRoute = ForbiddenRouteImport.update({ const ForbiddenRoute = ForbiddenRouteImport.update({
id: '/forbidden', id: '/forbidden',
@@ -107,12 +107,6 @@ const TransportationOpendockIndexRoute =
path: '/transportation/opendock/', path: '/transportation/opendock/',
getParentRoute: () => rootRouteImport, getParentRoute: () => rootRouteImport,
} as any) } as any)
const WarehouseDockdoorscanningDockScansRoute =
WarehouseDockdoorscanningDockScansRouteImport.update({
id: '/warehouse/dockdoorscanning/$dockScans',
path: '/warehouse/dockdoorscanning/$dockScans',
getParentRoute: () => rootRouteImport,
} as any)
const WarehouseDockdoorscanningDockRoute = const WarehouseDockdoorscanningDockRoute =
WarehouseDockdoorscanningDockRouteImport.update({ WarehouseDockdoorscanningDockRouteImport.update({
id: '/warehouse/dockdoorscanning/$dock', id: '/warehouse/dockdoorscanning/$dock',
@@ -134,6 +128,12 @@ const authUserProfileRoute = authUserProfileRouteImport.update({
path: '/user/profile', path: '/user/profile',
getParentRoute: () => rootRouteImport, getParentRoute: () => rootRouteImport,
} as any) } as any)
const WarehouseDockdoorscanningScansDockScansRoute =
WarehouseDockdoorscanningScansDockScansRouteImport.update({
id: '/warehouse/dockdoorscanning/scans/$dockScans',
path: '/warehouse/dockdoorscanning/scans/$dockScans',
getParentRoute: () => rootRouteImport,
} as any)
export interface FileRoutesByFullPath { export interface FileRoutesByFullPath {
'/': typeof IndexRoute '/': typeof IndexRoute
@@ -153,9 +153,9 @@ export interface FileRoutesByFullPath {
'/user/resetpassword': typeof authUserResetpasswordRoute '/user/resetpassword': typeof authUserResetpasswordRoute
'/user/signup': typeof authUserSignupRoute '/user/signup': typeof authUserSignupRoute
'/warehouse/dockdoorscanning/$dock': typeof WarehouseDockdoorscanningDockRoute '/warehouse/dockdoorscanning/$dock': typeof WarehouseDockdoorscanningDockRoute
'/warehouse/dockdoorscanning/$dockScans': typeof WarehouseDockdoorscanningDockScansRoute
'/transportation/opendock/': typeof TransportationOpendockIndexRoute '/transportation/opendock/': typeof TransportationOpendockIndexRoute
'/warehouse/dockdoorscanning/': typeof WarehouseDockdoorscanningIndexRoute '/warehouse/dockdoorscanning/': typeof WarehouseDockdoorscanningIndexRoute
'/warehouse/dockdoorscanning/scans/$dockScans': typeof WarehouseDockdoorscanningScansDockScansRoute
} }
export interface FileRoutesByTo { export interface FileRoutesByTo {
'/': typeof IndexRoute '/': typeof IndexRoute
@@ -175,9 +175,9 @@ export interface FileRoutesByTo {
'/user/resetpassword': typeof authUserResetpasswordRoute '/user/resetpassword': typeof authUserResetpasswordRoute
'/user/signup': typeof authUserSignupRoute '/user/signup': typeof authUserSignupRoute
'/warehouse/dockdoorscanning/$dock': typeof WarehouseDockdoorscanningDockRoute '/warehouse/dockdoorscanning/$dock': typeof WarehouseDockdoorscanningDockRoute
'/warehouse/dockdoorscanning/$dockScans': typeof WarehouseDockdoorscanningDockScansRoute
'/transportation/opendock': typeof TransportationOpendockIndexRoute '/transportation/opendock': typeof TransportationOpendockIndexRoute
'/warehouse/dockdoorscanning': typeof WarehouseDockdoorscanningIndexRoute '/warehouse/dockdoorscanning': typeof WarehouseDockdoorscanningIndexRoute
'/warehouse/dockdoorscanning/scans/$dockScans': typeof WarehouseDockdoorscanningScansDockScansRoute
} }
export interface FileRoutesById { export interface FileRoutesById {
__root__: typeof rootRouteImport __root__: typeof rootRouteImport
@@ -198,9 +198,9 @@ export interface FileRoutesById {
'/(auth)/user/resetpassword': typeof authUserResetpasswordRoute '/(auth)/user/resetpassword': typeof authUserResetpasswordRoute
'/(auth)/user/signup': typeof authUserSignupRoute '/(auth)/user/signup': typeof authUserSignupRoute
'/warehouse/dockdoorscanning/$dock': typeof WarehouseDockdoorscanningDockRoute '/warehouse/dockdoorscanning/$dock': typeof WarehouseDockdoorscanningDockRoute
'/warehouse/dockdoorscanning/$dockScans': typeof WarehouseDockdoorscanningDockScansRoute
'/transportation/opendock/': typeof TransportationOpendockIndexRoute '/transportation/opendock/': typeof TransportationOpendockIndexRoute
'/warehouse/dockdoorscanning/': typeof WarehouseDockdoorscanningIndexRoute '/warehouse/dockdoorscanning/': typeof WarehouseDockdoorscanningIndexRoute
'/warehouse/dockdoorscanning/scans/$dockScans': typeof WarehouseDockdoorscanningScansDockScansRoute
} }
export interface FileRouteTypes { export interface FileRouteTypes {
fileRoutesByFullPath: FileRoutesByFullPath fileRoutesByFullPath: FileRoutesByFullPath
@@ -222,9 +222,9 @@ export interface FileRouteTypes {
| '/user/resetpassword' | '/user/resetpassword'
| '/user/signup' | '/user/signup'
| '/warehouse/dockdoorscanning/$dock' | '/warehouse/dockdoorscanning/$dock'
| '/warehouse/dockdoorscanning/$dockScans'
| '/transportation/opendock/' | '/transportation/opendock/'
| '/warehouse/dockdoorscanning/' | '/warehouse/dockdoorscanning/'
| '/warehouse/dockdoorscanning/scans/$dockScans'
fileRoutesByTo: FileRoutesByTo fileRoutesByTo: FileRoutesByTo
to: to:
| '/' | '/'
@@ -244,9 +244,9 @@ export interface FileRouteTypes {
| '/user/resetpassword' | '/user/resetpassword'
| '/user/signup' | '/user/signup'
| '/warehouse/dockdoorscanning/$dock' | '/warehouse/dockdoorscanning/$dock'
| '/warehouse/dockdoorscanning/$dockScans'
| '/transportation/opendock' | '/transportation/opendock'
| '/warehouse/dockdoorscanning' | '/warehouse/dockdoorscanning'
| '/warehouse/dockdoorscanning/scans/$dockScans'
id: id:
| '__root__' | '__root__'
| '/' | '/'
@@ -266,9 +266,9 @@ export interface FileRouteTypes {
| '/(auth)/user/resetpassword' | '/(auth)/user/resetpassword'
| '/(auth)/user/signup' | '/(auth)/user/signup'
| '/warehouse/dockdoorscanning/$dock' | '/warehouse/dockdoorscanning/$dock'
| '/warehouse/dockdoorscanning/$dockScans'
| '/transportation/opendock/' | '/transportation/opendock/'
| '/warehouse/dockdoorscanning/' | '/warehouse/dockdoorscanning/'
| '/warehouse/dockdoorscanning/scans/$dockScans'
fileRoutesById: FileRoutesById fileRoutesById: FileRoutesById
} }
export interface RootRouteChildren { export interface RootRouteChildren {
@@ -289,9 +289,9 @@ export interface RootRouteChildren {
authUserResetpasswordRoute: typeof authUserResetpasswordRoute authUserResetpasswordRoute: typeof authUserResetpasswordRoute
authUserSignupRoute: typeof authUserSignupRoute authUserSignupRoute: typeof authUserSignupRoute
WarehouseDockdoorscanningDockRoute: typeof WarehouseDockdoorscanningDockRoute WarehouseDockdoorscanningDockRoute: typeof WarehouseDockdoorscanningDockRoute
WarehouseDockdoorscanningDockScansRoute: typeof WarehouseDockdoorscanningDockScansRoute
TransportationOpendockIndexRoute: typeof TransportationOpendockIndexRoute TransportationOpendockIndexRoute: typeof TransportationOpendockIndexRoute
WarehouseDockdoorscanningIndexRoute: typeof WarehouseDockdoorscanningIndexRoute WarehouseDockdoorscanningIndexRoute: typeof WarehouseDockdoorscanningIndexRoute
WarehouseDockdoorscanningScansDockScansRoute: typeof WarehouseDockdoorscanningScansDockScansRoute
} }
declare module '@tanstack/react-router' { declare module '@tanstack/react-router' {
@@ -401,13 +401,6 @@ declare module '@tanstack/react-router' {
preLoaderRoute: typeof TransportationOpendockIndexRouteImport preLoaderRoute: typeof TransportationOpendockIndexRouteImport
parentRoute: typeof rootRouteImport parentRoute: typeof rootRouteImport
} }
'/warehouse/dockdoorscanning/$dockScans': {
id: '/warehouse/dockdoorscanning/$dockScans'
path: '/warehouse/dockdoorscanning/$dockScans'
fullPath: '/warehouse/dockdoorscanning/$dockScans'
preLoaderRoute: typeof WarehouseDockdoorscanningDockScansRouteImport
parentRoute: typeof rootRouteImport
}
'/warehouse/dockdoorscanning/$dock': { '/warehouse/dockdoorscanning/$dock': {
id: '/warehouse/dockdoorscanning/$dock' id: '/warehouse/dockdoorscanning/$dock'
path: '/warehouse/dockdoorscanning/$dock' path: '/warehouse/dockdoorscanning/$dock'
@@ -436,6 +429,13 @@ declare module '@tanstack/react-router' {
preLoaderRoute: typeof authUserProfileRouteImport preLoaderRoute: typeof authUserProfileRouteImport
parentRoute: typeof rootRouteImport parentRoute: typeof rootRouteImport
} }
'/warehouse/dockdoorscanning/scans/$dockScans': {
id: '/warehouse/dockdoorscanning/scans/$dockScans'
path: '/warehouse/dockdoorscanning/scans/$dockScans'
fullPath: '/warehouse/dockdoorscanning/scans/$dockScans'
preLoaderRoute: typeof WarehouseDockdoorscanningScansDockScansRouteImport
parentRoute: typeof rootRouteImport
}
} }
} }
@@ -457,10 +457,10 @@ const rootRouteChildren: RootRouteChildren = {
authUserResetpasswordRoute: authUserResetpasswordRoute, authUserResetpasswordRoute: authUserResetpasswordRoute,
authUserSignupRoute: authUserSignupRoute, authUserSignupRoute: authUserSignupRoute,
WarehouseDockdoorscanningDockRoute: WarehouseDockdoorscanningDockRoute, WarehouseDockdoorscanningDockRoute: WarehouseDockdoorscanningDockRoute,
WarehouseDockdoorscanningDockScansRoute:
WarehouseDockdoorscanningDockScansRoute,
TransportationOpendockIndexRoute: TransportationOpendockIndexRoute, TransportationOpendockIndexRoute: TransportationOpendockIndexRoute,
WarehouseDockdoorscanningIndexRoute: WarehouseDockdoorscanningIndexRoute, WarehouseDockdoorscanningIndexRoute: WarehouseDockdoorscanningIndexRoute,
WarehouseDockdoorscanningScansDockScansRoute:
WarehouseDockdoorscanningScansDockScansRoute,
} }
export const routeTree = rootRouteImport export const routeTree = rootRouteImport
._addFileChildren(rootRouteChildren) ._addFileChildren(rootRouteChildren)

View File

@@ -120,6 +120,10 @@ export default function NewArticleLink({ refetch }: { refetch: any }) {
//TODO: get the docks from lst to help refine and actually link the dock correctly //TODO: get the docks from lst to help refine and actually link the dock correctly
const dock = [ const dock = [
{
label: "Default",
value: "default",
},
{ {
label: "Cermac", label: "Cermac",
value: "cermac", value: "cermac",

View File

@@ -1,6 +1,7 @@
import { useSuspenseQuery } from "@tanstack/react-query"; import { useSuspenseQuery } from "@tanstack/react-query";
import { createFileRoute } from "@tanstack/react-router"; import { createFileRoute, useNavigate } from "@tanstack/react-router";
import { format } from "date-fns"; import { format } from "date-fns";
import { toast } from "sonner";
import { Button } from "../../../components/ui/button"; import { Button } from "../../../components/ui/button";
import { import {
Card, Card,
@@ -10,108 +11,155 @@ import {
CardHeader, CardHeader,
} from "../../../components/ui/card"; } from "../../../components/ui/card";
import { Separator } from "../../../components/ui/separator"; import { Separator } from "../../../components/ui/separator";
import { api } from "../../../lib/apiHelper";
import { getActiveLoadingOrders } from "../../../lib/queries/getActiveDockScanners"; import { getActiveLoadingOrders } from "../../../lib/queries/getActiveDockScanners";
import { getActiveDockScanners } from "../../../lib/queries/getActiveLoadingOrders"; import { getActiveDockScanners } from "../../../lib/queries/getActiveLoadingOrders";
import { finishLoadingOrder} from './index' import { finishLoadingOrder } from "./index";
import { api } from "../../../lib/apiHelper";
import { toast } from "sonner";
export const Route = createFileRoute("/warehouse/dockdoorscanning/$dock")({ export const Route = createFileRoute("/warehouse/dockdoorscanning/$dock")({
component: RouteComponent, component: RouteComponent,
}); });
export const startOrder = async (loadingOrder: string, dockId: string, refetch:any, refetchActiveLoading:any) => { export const startOrder = async (
loadingOrder: string,
dockId: string,
refetch: any,
refetchActiveLoading: any,
) => {
try { try {
const res = await api.post("/dockDoor/startLoad", { const res = await api.post(
"loadingOrder":String(loadingOrder), "/dockDoor/startLoad",
"dockId":dockId {
},{validateStatus: (status) => status < 500,}) loadingOrder: String(loadingOrder),
dockId: dockId,
},
{ validateStatus: (status) => status < 500 },
);
if (!res.data.success) { if (!res.data.success) {
toast.error(res.data.message) toast.error(res.data.message);
refetch() refetch();
refetchActiveLoading() refetchActiveLoading();
return return;
} }
toast.success(res.data.message) toast.success(res.data.message);
refetch() refetch();
refetchActiveLoading() refetchActiveLoading();
} catch (error) { } catch (error) {
console.log(error) console.log(error);
toast.error(`Encountered error: ${JSON.stringify(error)}`) toast.error(`Encountered error: ${JSON.stringify(error)}`);
} }
};
}
function RouteComponent() { function RouteComponent() {
const { dock } = Route.useParams(); const { dock } = Route.useParams();
const { data, refetch } = useSuspenseQuery(getActiveDockScanners()); const { data, refetch } = useSuspenseQuery(getActiveDockScanners());
const { data: loadingPlanItems, refetch: refetchActiveLoading } = useSuspenseQuery(getActiveLoadingOrders()); const { data: loadingPlanItems, refetch: refetchActiveLoading } =
useSuspenseQuery(getActiveLoadingOrders());
const navigate = useNavigate();
const dockData = data.filter((i: any) => i.dockId === dock); const dockData = data.filter((i: any) => i.dockId === dock);
const loadingPlans = loadingPlanItems.filter( const loadingPlans = loadingPlanItems.filter(
(l: any) => l.dockId === Number(dock), (l: any) => l.dockId === Number(dock),
); );
console.log(dockData[0].currentLoadingOrder === "");
return ( return (
<div className="flex flex-col"> <div className="flex flex-col">
<div className="flex justify-center"> <div className="flex justify-center">
<p>Please select an active loading order for {dockData[0].name}</p> <p>Please select an active loading order for {dockData[0].name}</p>
</div> </div>
<div className="flex justify-center mt-5 gap-2"> <div className="flex justify-center mt-5 gap-2">
{loadingPlans && {loadingPlans && loadingPlans.length > 0 ? (
loadingPlans.length > 0 && <div>
loadingPlans.map((i: any) => { {loadingPlans.map((i: any) => {
return ( return (
<Card key={i.id} className="max-w-96"> <Card key={i.id} className="max-w-96">
<CardHeader> <CardHeader>
Loading order ID: {i.id}{" "} Loading order ID: {i.id}{" "}
<p> <p>
Loading Date: {format(i.loadingDate, "MM/dd/yyyy HH:mm")} Loading Date: {format(i.loadingDate, "MM/dd/yyyy HH:mm")}
</p> </p>
</CardHeader> </CardHeader>
<CardDescription className=""> <CardDescription className="">
<p className="p-3"> <p className="p-3">
Below are the loading order details please validate the Below are the loading order details please validate the
loading order you are selecting before pressing start. loading order you are selecting before pressing start.
</p> </p>
</CardDescription> </CardDescription>
{/* Mapping the items out so in case we have more than 1 it will display correctly */} {/* Mapping the items out so in case we have more than 1 it will display correctly */}
<CardContent> <CardContent>
{i?.loadingPlanItems?.map((l: any) => { {i?.loadingPlanItems?.map((l: any) => {
return ( return (
<div key={i.id}> <div key={i.id}>
<p>Loading Sequence {l.loadingSequence}</p> <p>Loading Sequence {l.loadingSequence}</p>
<p> <p>
Article: {l.articleId} - {l.articleDescription} Article: {l.articleId} - {l.articleDescription}
</p> </p>
<p> <p>
Current loaded: {l.loadedQuantityLUs}/ Current loaded: {l.loadedQuantityLUs}/
{l.plannedQuantityLUs} {l.plannedQuantityLUs}
</p> </p>
{l.remark !== "" && <p>Remark: {l.remark}</p>} {l.remark !== "" && <p>Remark: {l.remark}</p>}
{i?.loadingPlanItems.length > 1 && ( {i?.loadingPlanItems.length > 1 && (
<Separator className="m-2" /> <Separator className="m-2" />
)} )}
</div> </div>
); );
})} })}
</CardContent> </CardContent>
<CardFooter> <CardFooter>
<div className="flex flex-row justify-between"> <div className="flex flex-row justify-between">
<Button <Button
onClick={()=> startOrder(i.id, dock, refetch, refetchActiveLoading)} onClick={() =>
disabled={dockData[0].currentLoadingOrder !== "" ? true : false}>Start Loading</Button> startOrder(i.id, dock, refetch, refetchActiveLoading)
<Button>Scan progress</Button> }
<Button onClick={()=> finishLoadingOrder(String(i.id), dock, refetch, refetchActiveLoading)} disabled={
disabled={dockData[0].currentLoadingOrder === "" ? true : false}>Finish Loading</Button> dockData[0].currentLoadingOrder !== "" ? true : false
</div> }
</CardFooter> >
</Card> Start Loading
); </Button>
})} <Button
onClick={() =>
navigate({
to: "/warehouse/dockdoorscanning/scans/$dockScans",
params: { dockScans: dock },
})
}
>
Scan progress
</Button>
<Button
onClick={() =>
finishLoadingOrder(
String(i.id),
dock,
refetch,
refetchActiveLoading,
)
}
disabled={
dockData[0].currentLoadingOrder === "" ? true : false
}
>
Finish Loading
</Button>
</div>
</CardFooter>
</Card>
);
})}
</div>
) : (
<div>
<p>There are know loading orders currently active.</p>
<p>
Head over to Outbound deliveries to create a loading order to
start the flow
</p>
</div>
)}
</div> </div>
</div> </div>
); );

View File

@@ -1,10 +0,0 @@
import { createFileRoute } from "@tanstack/react-router";
export const Route = createFileRoute("/warehouse/dockdoorscanning/$dockScans")({
component: RouteComponent,
});
function RouteComponent() {
const { dockScans } = Route.useParams();
return <div>Hello "/warehouse/dockdoorscanning/$docScans"! {dockScans}</div>;
}

View File

@@ -1,43 +1,58 @@
import { useSuspenseQuery } from "@tanstack/react-query"; import { useSuspenseQuery } from "@tanstack/react-query";
import { createFileRoute, useNavigate } from "@tanstack/react-router"; import { createFileRoute, Link, useNavigate } from "@tanstack/react-router";
import { Card, CardContent, CardDescription, CardHeader } from "../../../components/ui/card"; import { toast } from "sonner";
import { Button } from "../../../components/ui/button";
import {
Card,
CardContent,
CardDescription,
CardHeader,
} from "../../../components/ui/card";
import { api } from "../../../lib/apiHelper";
import { getActiveLoadingOrders } from "../../../lib/queries/getActiveDockScanners"; import { getActiveLoadingOrders } from "../../../lib/queries/getActiveDockScanners";
import { getActiveDockScanners } from "../../../lib/queries/getActiveLoadingOrders"; import { getActiveDockScanners } from "../../../lib/queries/getActiveLoadingOrders";
import { Button } from "../../../components/ui/button";
import { api } from "../../../lib/apiHelper";
import { toast } from "sonner";
export const Route = createFileRoute("/warehouse/dockdoorscanning/")({ export const Route = createFileRoute("/warehouse/dockdoorscanning/")({
component: RouteComponent, component: RouteComponent,
}); });
export const finishLoadingOrder = async (loadingOrder: string, dockId: string, refetch:any, refetchActiveLoading:any) => { export const finishLoadingOrder = async (
loadingOrder: string,
dockId: string,
refetch: any,
refetchActiveLoading: any,
) => {
try { try {
const res = await api.post("/dockDoor/finishOrder", { const res = await api.post(
"loadingOrder":loadingOrder, "/dockDoor/finishOrder",
"dockId":dockId {
},{validateStatus: (status) => status < 500,}) loadingOrder: loadingOrder,
dockId: dockId,
},
{ validateStatus: (status) => status < 500 },
);
if (!res.data.success) { if (!res.data.success) {
toast.error(res.data.message) toast.error(res.data.message);
refetch() refetch();
refetchActiveLoading() refetchActiveLoading();
return return;
} }
toast.info(res.data.message) toast.info(res.data.message);
refetch() refetch();
refetchActiveLoading() refetchActiveLoading();
} catch (error) { } catch (error) {
console.log(error) console.log(error);
toast.error(`Encountered error: ${JSON.stringify(error)}`) toast.error(`Encountered error: ${JSON.stringify(error)}`);
} }
};
}
function RouteComponent() { function RouteComponent() {
const { data, isLoading, refetch } = useSuspenseQuery(getActiveDockScanners()); const { data, isLoading, refetch } = useSuspenseQuery(
const { data: loadingPlanItems, refetch : refetchActiveLoading } = useSuspenseQuery(getActiveLoadingOrders()); getActiveDockScanners(),
);
const { data: loadingPlanItems, refetch: refetchActiveLoading } =
useSuspenseQuery(getActiveLoadingOrders());
const navigate = useNavigate(); const navigate = useNavigate();
if (isLoading) { if (isLoading) {
@@ -47,6 +62,7 @@ function RouteComponent() {
</div> </div>
); );
} }
return ( return (
<div className="flex flex-col "> <div className="flex flex-col ">
<div className="flex justify-center-safe"> <div className="flex justify-center-safe">
@@ -64,8 +80,8 @@ function RouteComponent() {
(x: any) => x.id === Number(i.currentLoadingOrder), (x: any) => x.id === Number(i.currentLoadingOrder),
) )
: []; : [];
console.log(loadingPlan);
console.log(loadingPlanItems);
return ( return (
<Card <Card
key={i.id} key={i.id}
@@ -83,7 +99,9 @@ function RouteComponent() {
}} }}
> >
<CardHeader className="text-center">{i.name}</CardHeader> <CardHeader className="text-center">{i.name}</CardHeader>
<CardDescription>For Abbott loads reminder: 3 lots per load max.</CardDescription> <CardDescription>
For Abbott loads reminder: 3 lots per load max.
</CardDescription>
{i.currentLoadingOrder !== "" ? ( {i.currentLoadingOrder !== "" ? (
<CardContent> <CardContent>
@@ -92,19 +110,55 @@ function RouteComponent() {
</div> </div>
<div> <div>
{loadingPlan && loadingPlan.length !== 0 ? (
<>
{loadingPlan && loadingPlan.length !== 0 ? (<> <p>{`${loadingPlan[0].loadingPlanItems[0].articleId} - ${loadingPlan[0].loadingPlanItems[0].articleDescription}`}</p>
<p>
<p>{`${loadingPlan[0].loadingPlanItems[0].articleId} - ${loadingPlan[0].loadingPlanItems[0].articleDescription}`}</p> Current Loaded :{" "}
{
<p>Current Loaded :{" "} loadingPlan[0].loadingPlanItems[0]
{loadingPlan[0].loadingPlanItems[0].loadedQuantityLUs} /{" "} .loadedQuantityLUs
{loadingPlan[0].loadingPlanItems[0].plannedQuantityLUs}</p></> }{" "}
): <><p>The Current Loading order is invalid</p> /{" "}
<p> It appears it could have been finished via another process</p> {
<div className="m-2 flex justify-center"> loadingPlan[0].loadingPlanItems[0]
<Button onClick={()=> finishLoadingOrder(i.currentLoadingOrder, i.dockId, refetch, refetchActiveLoading)}>Clear {i.currentLoadingOrder}</Button></div></>}</div> .plannedQuantityLUs
}
</p>
Check Scans:{" "}
<Link
to={"/warehouse/dockdoorscanning/scans/$dockScans"}
params={{ dockScans: i.dockId }}
className="underline"
>
CLICK HERE
</Link>
</>
) : (
<>
<p>The Current Loading order is invalid</p>
<p>
{" "}
It appears it could have been finished via another
process
</p>
<div className="m-2 flex justify-center">
<Button
onClick={() =>
finishLoadingOrder(
i.currentLoadingOrder,
i.dockId,
refetch,
refetchActiveLoading,
)
}
>
Clear {i.currentLoadingOrder}
</Button>
</div>
</>
)}
</div>
</CardContent> </CardContent>
) : ( ) : (
<CardContent> <CardContent>

View File

@@ -0,0 +1,198 @@
import { useSuspenseQuery } from "@tanstack/react-query";
import { createFileRoute } from "@tanstack/react-router";
import { createColumnHelper } from "@tanstack/react-table";
import { formatInTimeZone } from "date-fns-tz";
import { toast } from "sonner";
import { Button } from "../../../../components/ui/button";
import { useSocketRoom } from "../../../../hooks/socket.io.hook";
import { api } from "../../../../lib/apiHelper";
import { useAppForm } from "../../../../lib/formSutff";
import { getActiveLoadingOrders } from "../../../../lib/queries/getActiveDockScanners";
import { getActiveDockScanners } from "../../../../lib/queries/getActiveLoadingOrders";
import LstTable from "../../../../lib/tableStuff/LstTable";
import SearchableHeader from "../../../../lib/tableStuff/SearchableHeader";
import { finishLoadingOrder } from "..";
export const Route = createFileRoute(
"/warehouse/dockdoorscanning/scans/$dockScans",
)({
component: RouteComponent,
});
function RouteComponent() {
const { dockScans } = Route.useParams();
const { data: logs, clearRoom } = useSocketRoom<any>(
`dockDoorLoading:${dockScans}`,
);
const { data, refetch } = useSuspenseQuery(getActiveDockScanners());
const { data: loadingPlanItems, refetch: refetchActiveLoading } =
useSuspenseQuery(getActiveLoadingOrders());
const columnHelper = createColumnHelper<any>();
const column = [
columnHelper.accessor("loadingOrder", {
header: ({ column }) => (
<SearchableHeader column={column} title="Loading Order" />
),
filterFn: "includesString",
cell: (i) => i.getValue(),
}),
columnHelper.accessor("loadingUnit", {
header: ({ column }) => (
<SearchableHeader column={column} title="Loading Unit" />
),
filterFn: "includesString",
cell: (i) => i.getValue(),
}),
columnHelper.accessor("loadingUnitStatus", {
header: ({ column }) => (
<SearchableHeader column={column} title="Status" />
),
filterFn: "includesString",
cell: (i) => i.getValue(),
}),
columnHelper.accessor("message", {
header: ({ column }) => (
<SearchableHeader column={column} title="Message" />
),
filterFn: "includesString",
cell: (i) => i.getValue(),
}),
columnHelper.accessor("upd_date", {
header: ({ column }) => (
<SearchableHeader column={column} title="Scanned At" />
),
filterFn: "includesString",
cell: (i) => {
function isDateValid(date: any) {
return date instanceof Date && !isNaN(date.getTime());
}
const trueDate = isDateValid(new Date(i.getValue()))
? formatInTimeZone(
i.getValue(),
`${window.LST_CONFIG?.timezone}`,
"MM/dd/yyyy HH:mm:ss",
)
: "invalid time";
return <span>{trueDate}</span>;
},
}),
columnHelper.accessor("status", {
header: ({ column }) => (
<SearchableHeader column={column} title="Status" />
),
filterFn: "includesString",
cell: (i) => i.getValue(),
}),
];
const form = useAppForm({
defaultValues: {
runningNo: "",
dockId: data[0].dockId,
},
onSubmit: async ({ value }) => {
try {
const res = await api.post("/dockDoor/loadUnit", value, {
validateStatus: (status) => status < 500,
});
refetchActiveLoading();
form.reset();
if (!res.data.success) {
toast.error(res.data.data.message);
return;
}
toast.success(res.data.message);
} catch (error) {
console.log(error);
}
},
});
const loadingPlan =
data[0].currentLoadingOrder !== ""
? loadingPlanItems.filter(
(x: any) => x.id === Number(data[0].currentLoadingOrder),
)
: [];
return (
<div>
<div>
<p className="text-2xl text-center">
You are monitoring scans for {data[0].name}
</p>
<p className="text-center">
Current load status:{" "}
{loadingPlan && loadingPlan.length !== 0 ? (
<span>
{loadingPlan[0].loadingPlanItems[0].loadedQuantityLUs} /{" "}
{loadingPlan[0].loadingPlanItems[0].plannedQuantityLUs}
</span>
) : (
<span>"No active loading orders</span>
)}
</p>
</div>
<div className="max-w-1/2 flex flex-col">
<div>
<form
onSubmit={(e) => {
e.preventDefault();
form.handleSubmit();
}}
>
<div className="flex flex-row">
<div className="mb-2 mr-2 max-w-48">
<form.AppField name="runningNo">
{(field) => (
<field.InputField
label="Running Number"
inputType="text"
required={true}
/>
)}
</form.AppField>
</div>
<div className="flex justify-end mt-8 mr-3 ">
<form.AppForm>
<form.SubmitButton>Submit</form.SubmitButton>
</form.AppForm>
</div>
</div>
</form>
</div>
<div className="flex justify-end mr-3 ">
<Button
type="button"
onClick={() => {
finishLoadingOrder(
String(data[0].currentLoadingOrder),
dockScans,
refetch,
refetchActiveLoading,
);
clearRoom();
}}
disabled={
loadingPlan ||
loadingPlan[0].loadingPlanItems[0].loadedQuantityLUs !==
loadingPlan[0].loadingPlanItems[0].plannedQuantityLUs
}
>
Finish Loading order
</Button>
<Button onClick={() => clearRoom()}>Clear Table</Button>
</div>
</div>
<div>
<LstTable data={logs} columns={column} pageSize={50} />
</div>
</div>
);
}

View File

@@ -0,0 +1 @@
ALTER TABLE "dock_door_scans" DROP CONSTRAINT "dock_door_scans_loading_Unit_unique";

File diff suppressed because it is too large Load Diff

View File

@@ -435,6 +435,13 @@
"when": 1780692629119, "when": 1780692629119,
"tag": "0061_wide_marrow", "tag": "0061_wide_marrow",
"breakpoints": true "breakpoints": true
},
{
"idx": 62,
"version": "7",
"when": 1781009330205,
"tag": "0062_square_harrier",
"breakpoints": true
} }
] ]
} }