updateShipmentStatus
Update the status of one shipment, keyed by the shipment UUID. The order-level shipment_status rollup is recomputed afterwards.
Import
import { updateShipmentStatus } from "@evershop/evershop/oms/services";
Syntax
updateShipmentStatus(
shipmentUuid: string,
status: string,
conn?: PoolClient
): Promise<void>
This function is keyed on the shipment UUID, not the order id. The old updateShipmentStatus(orderId, status) form is gone — an order can have many shipments, so there is no single shipment status to set from an order id. To move a whole order, load its shipments and call this per shipment.
Parameters
shipmentUuid
Type: string
The shipment.uuid of the shipment to update. Throws Shipment not found: <uuid> when it does not exist.
status
Type: string
The target per-shipment status code. Must be registered in oms.order.shipmentStatus (core registers shipped, delivered, canceled), otherwise throws Invalid status: <status>.
conn (optional)
Type: PoolClient
An existing connection with an open transaction. When omitted, the function opens and commits its own.
Return Value
Returns Promise<void>.
Examples
Mark a shipment delivered
import { updateShipmentStatus } from "@evershop/evershop/oms/services";
await updateShipmentStatus('3f1c2b7a-8d4e-4f21-9d0b-2c9a51f6e0aa', 'delivered');
Update every shipment on an order
import {
getShipmentsForOrder,
updateShipmentStatus
} from "@evershop/evershop/oms/services";
// getShipmentsForOrder accepts an order id or an order uuid
const shipments = await getShipmentsForOrder(orderUuid);
for (const shipment of shipments) {
await updateShipmentStatus(shipment.uuid, 'delivered');
}
Phase transitions
Every registered shipment status declares a phase (shipped, delivered or canceled). Transitions are validated by phase, not by status code:
| From phase | Allowed target phases |
|---|---|
shipped | shipped, delivered, canceled |
delivered | delivered (terminal) |
canceled | canceled (terminal) |
Same-phase moves are always allowed, so in_transit → out_for_delivery (both shipped) is fine. Anything else throws Cannot transition shipment from phase <from> to phase <to>.
The first time a shipment enters a phase, the corresponding timestamp column is stamped: shipped_at, delivered_at or canceled_at. Re-entering the same phase does not overwrite it.
Order rollup
After the shipment row is written, recomputeOrderShipmentStatus() recalculates the order-level order.shipment_status from all of the order's shipments and their item quantities. That rollup value is one of pending, partially_shipped, shipped, partially_delivered, delivered, partially_canceled, canceled — and it, not the per-shipment status, is what the psoMapping matches to re-resolve order.status.
Events
| Event | When | Payload |
|---|---|---|
shipment_status_changed | Always, after commit | { shipmentId, orderId, from, to, phase } |
shipment_delivered | When the new status's phase is delivered | { shipmentId, orderId } |
Notes
- Hookable at
updateShipmentStatus,validateShipmentStatusBeforeUpdateandchangeShipmentStatusForShipment. - Events are emitted after the commit when the function owns the transaction; when you pass your own
conn, they are routed through it so subscribers never observe uncommitted state.
See Also
- createShipment - Create a shipment
- registerShipmentStatus - Register a custom shipment status
- updatePaymentStatus - Update payment status