API Reference
The ScanPick API exposes REST endpoints for all operations.
In development mode (ASPNETCORE_ENVIRONMENT=Development), a fully interactive
API explorer is available at the Scalar UI endpoint.
Base URL
Section titled “Base URL”http://<host>:<port>/apiAuthentication
Section titled “Authentication”All endpoints except /api/auth/login require a JWT in the Authorization header:
Authorization: Bearer <token>POST /api/auth/login
Section titled “POST /api/auth/login”Authenticate a worker by PIN and receive a JWT.
Request:
{ "workerId": "worker-001", "pin": "1234"}Response:
{ "token": "eyJhbGci...", "workerId": "worker-001", "name": "Alice Manager", "role": "manager", "expiresAt": "2026-06-21T12:00:00Z"}GET /api/waves
Section titled “GET /api/waves”List all waves with optional status filter.
Query Parameters:
status— filter by status:Pending,InProgress,Completed,CancelledassignedWorkerId— filter by assigned worker
Response:
[ { "id": "wave-001", "name": "Wave-001", "status": "InProgress", "assignedWorkerId": "worker-003", "assignedWorkerName": "Charlie Picker", "totalPickTasks": 5, "completedPickTasks": 2, "skippedPickTasks": 1, "createdAt": "2026-06-19T08:00:00Z" }]POST /api/waves
Section titled “POST /api/waves”Create a new wave.
Request:
{ "name": "Wave-004", "orderIds": ["order-001", "order-002"]}GET /api/waves/{id}
Section titled “GET /api/waves/{id}”Get wave detail including orders, pick tasks, and items.
DELETE /api/waves/{id}
Section titled “DELETE /api/waves/{id}”Cancel a wave (must be in Pending status).
POST /api/waves/{id}/start
Section titled “POST /api/waves/{id}/start”Start a wave. Consolidates items into pick tasks and transitions to InProgress.
Request:
{ "assignedWorkerId": "worker-003"}POST /api/waves/{id}/assign
Section titled “POST /api/waves/{id}/assign”(Re)assign a worker to a wave.
POST /api/waves/{id}/complete
Section titled “POST /api/waves/{id}/complete”Mark a wave as Completed. All pick tasks must be picked or skipped.
Picking
Section titled “Picking”GET /api/picking/waves/{waveId}/tasks
Section titled “GET /api/picking/waves/{waveId}/tasks”Get all pick tasks for a wave, sorted by optimized pick path.
Response:
[ { "id": "picktask-001", "productName": "Widget Alpha", "expectedBarcode": "5901234567890", "quantity": 10, "pickedQuantity": 3, "status": "InProgress", "zone": "A", "aisle": "01", "rack": "03", "shelf": "02", "bin": "01", "sortPath": "01-03-02" }]POST /api/picking/submit-scan
Section titled “POST /api/picking/submit-scan”Submit a pick scan from the mobile device. Supports offline idempotency via client-generated UUID.
Request:
{ "pickTaskId": "picktask-001", "barcode": "5901234567890", "scannedAt": "2026-06-19T10:30:00Z", "idempotencyKey": "a1b2c3d4-e5f6-...", "workerId": "worker-003"}Response:
{ "success": true, "pickTaskId": "picktask-001", "newPickedQuantity": 4, "pickTaskStatus": "InProgress", "remainingQuantity": 6}POST /api/picking/skip-task
Section titled “POST /api/picking/skip-task”Skip a pick task with a reason (discrepancy reporting).
Request:
{ "pickTaskId": "picktask-003", "reason": "Damaged", "workerId": "worker-003"}Values for reason: Damaged, OutOfStock, WrongLocation, Other
Warehouse
Section titled “Warehouse”GET /api/warehouse
Section titled “GET /api/warehouse”Get warehouse details with zones and location counts.
POST /api/warehouse/setup
Section titled “POST /api/warehouse/setup”Initialize warehouse with zones and generate locations.
GET /api/locations
Section titled “GET /api/locations”List locations with optional filters (zone, occupied status).
PUT /api/locations/{id}
Section titled “PUT /api/locations/{id}”Update location metadata (description, etc.).
POST /api/locations/generate
Section titled “POST /api/locations/generate”Bulk generate locations from zone configuration.
Health
Section titled “Health”GET /api/health
Section titled “GET /api/health”Health check endpoint. Returns 200 OK when the API is running and database is reachable.
SignalR Hub
Section titled “SignalR Hub”/pickhub
Section titled “/pickhub”Real-time hub for pushing scan events to connected clients.
Methods (server → client):
PickTaskUpdated— a pick task’s picked quantity changedWaveProgressUpdated— wave completion statistics changedWorkerScanned— another worker’s scan activity (supervisor view)
Methods (client → server):
SubscribeToWave(waveId)— subscribe to updates for a specific waveUnsubscribeFromWave(waveId)— unsubscribe
All SignalR methods use single object parameters for backward-compatible schema evolution.
Error Responses
Section titled “Error Responses”All endpoints return consistent error responses:
{ "error": { "code": "VALIDATION_ERROR", "message": "A human-readable error message", "details": [ { "field": "workerId", "message": "Worker ID is required" } ] }}Common HTTP status codes:
400— Bad request (validation error)401— Unauthorized (missing or invalid JWT)403— Forbidden (insufficient role)404— Resource not found409— Conflict (invalid status transition)500— Internal server error