Announce a package

POST /api/v1/inbound-shipments write:inbound_shipment

Tells us a package of your cards is on its way. Send the carrier tracking number as soon as the label exists, and the site — the warehouse the label is addressed to (list them with GET /sites). Each warehouse works only its own incoming list, so a package with the wrong site is not expected where it lands; it is still received there, and received_site then differs from destination_site. When the box reaches the warehouse, the receiving operator scans its label and the shipment moves to RECEIVED. Read that back with GET /inbound-shipments/:id, or wait for the inbound_shipment.received event on your activity log. Received means the box is on our floor, not that its cards are intaken; those still appear one by one in GET /cards as they are scanned. Announcing the same box twice is safe. If you already have a live announcement for this tracking number, or we received a box with it in the last 120 days, you get that shipment back with 200 and created: false instead of a duplicate. Re-announcing a box we already have is therefore a quick way to learn it arrived. To change where a box is going, cancel it and announce it again with the right site. We match on letters and digits only (spaces, dashes and case are ignored), and a USPS or FedEx label barcode matches even though it carries extra digits around the tracking number. Send exactly the number the carrier gave you.

This endpoint needs its own write:inbound_shipment scope. Ask your account manager to add it to your key; no existing scope stands in for it.

Try it POST /api/v1/inbound-shipments write
request body
object · 6 keys
{
  "tracking_number": "9400111899223197428490",
  "site": "oregon-1",
  "carrier": "usps",
  "card_count": 120,
  "reference": "PO-1001",
  "idempotency_key": "docs-inbound-9400111899223197428490"
}
response

Not run yet. Press Run to make a live call against https://service.rip.fun (through this demo's server-side proxy; the API key never reaches the browser).

curl (tracks the inputs above)
curl -X POST 'https://service.rip.fun/api/v1/inbound-shipments' \
  -H 'X-API-Key: rip_…' \
  -H 'Content-Type: application/json' \
  -d '{"tracking_number":"9400111899223197428490","site":"oregon-1","carrier":"usps","card_count":120,"reference":"PO-1001","idempotency_key":"docs-inbound-9400111899223197428490"}'

Request fields

FieldTypeRequiredDescription
tracking_numberstringyesThe carrier tracking number, up to 64 chars. Must contain 8–64 letters or digits once spaces and punctuation are removed
sitestringyesThe warehouse the package is addressed to, by site code — today "oregon-1", the only site receiving packages. Matched case-insensitively. Must be one of the codes GET /sites returns; a missing code, an unknown one, or a site that is not receiving packages returns 400 naming the valid ones
carrierstringFree text, up to 32 chars, stored lower-cased: "usps", "ups", "fedex", "dhl", …
card_countintHow many cards are in the box, 0..100000. Shown to the receiving operator; informational — nothing is billed on it
referencestringYour own reference for the box (PO, batch, consignment id), up to 128 chars
notestringUp to 512 chars
idempotency_keystringUp to 128 chars; a replay returns the original shipment with 200 and created: false

Response fields (data)

FieldDescription
inbound_shipment.id / tracking_number / carrier / card_count / reference / noteWhat you submitted (tracking_number as sent, trimmed)
inbound_shipment.destination_site{ code, name } — the site you addressed it to. null only on packages announced before sites were required
inbound_shipment.received_site{ code, name } — where it was actually scanned in; null until it is received. Differs from destination_site when a box arrived at the other warehouse
inbound_shipment.status"EXPECTED" on create; EXPECTED → RECEIVED when the warehouse scans it in, or EXPECTED → CANCELLED if you cancel it first
inbound_shipment.source"tenant" for a package you announced; "warehouse" for one that arrived unannounced and was logged against your account at the door
inbound_shipment.created_at / received_at / cancelled_at / updated_atTimestamps; received_at and cancelled_at are null until they happen
createdtrue (201) when this request recorded the announcement; false (200) when the box was already on file

Errors

StatusCodeWhen
400invalid sitesite missing, unknown, or a warehouse that is not receiving packages ("texas-1 is not receiving packages — send them to: oregon-1")
409no site receivingno warehouse is taking packages at all right now — contact your account manager
400invalid inputtracking_number missing or too short/long, card_count not a whole number in range, a text field over its limit, or idempotency_key over 128 chars
403Insufficient permissionskey is tenant-scoped but carries neither write:inbound_shipment nor admin

See Errors for the response envelope and the full code list.