Receiving & box scanning
Box-level scanning is how a small operation gets a real WMS workflow without a real WMS. Every received unit is traceable to a specific box, and your warehouse team picks from one box at a time so the next box's labels stay on it until you need them.
What "box-level" means
When you receive a PO, the app generates one receipt box per pre-set unit count. A 5,000-unit PO with 100 units per box gives you 50 boxes. Each box gets:
- A unique workspace-scoped barcode (e.g.
K9-42) - A printed label with the SKU, qty, and PO reference
- A state:
UNOPENED→OPEN→DEPLETED
Boxes give your warehouse team a physical handle on the inventory: which box is open, which one to pull from next, which ones are still sealed.
Generating boxes
When you click Receive on a PO, the receipt page asks for units per box. The app then creates the right number of boxes per receipt line. You can edit the count if your supplier's pack-out is non-standard.
Boxes are unique per workspace, not globally — your K9-42 and another tenant's K9-42 won't collide.
Printing labels
After receiving, open the receipt detail page and click Print labels. Two sizes:
- Large (4×6") — portrait, default. Works on a thermal label printer
- Small (3×2") — landscape, toggleable
Four design variants: classic, editorial, bold, minimal. Tack ?variant=bold (or any other) onto the URL to switch. Real Code-128 barcodes render via bwip-js; they scan reliably on phone cameras and 1D scanners.
A note on print stylesheets: most browsers don't print background colors by default. The labels use borders instead of background fills so they print cleanly without you needing to enable "Background graphics" in the print dialog.
Scanning to deplete
Open Receiving in the sidebar. Two paths to enter a code:
- Text input — type the box code, hit enter
- Camera scanner — point your phone at the barcode (uses the device's camera via
@zxing/browser)
Scanning a code:
- If the box is
UNOPENED: marks itOPENand depletes any previously open box for the same SKU (one open box per SKU is the rule) - If the box is
OPEN: nothing happens — already in use - If the box is
DEPLETED: shows an error
The "Mark depleted" checkbox lets you flag a box as fully consumed in one shot — useful for gift events, single-customer pulls, or cases where you don't open a fresh box.
Box state and inventory
Box state is operational, not financial. Opening or depleting a box does not move inventory cost. Inventory is reduced via:
- Sales import (Shopify/Amazon CSV → outbound
SALEmovements) - Write-offs (
WRITE_OFFmovements with a reason code) - Cycle-count adjustments (
COUNT_ADJUSTMENTmovements)
Box state is just the warehouse team's signal for which physical box to grab from next. The cost ledger and box state are independent ledgers that happen to share the same product.
Phone camera + HTTPS
iOS Safari blocks getUserMedia on plain http:// (except on localhost). For phone-camera testing during dev, route through an ngrok HTTPS tunnel. In production this is a non-issue — the deployed app is on HTTPS by default.