Skip to main content

Routes

16 API calls in this section.

List Routes

Delivery & Last-Mile / Routes
GET/delivery/routes?page=1&limit=20&status=&driver_id=&search=&include_inactive=false

List active routes with optional filters. Excludes inactive routes by default.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request GET "$ONDI_BASE_URL/delivery/routes?page=1&limit=20&status=&driver_id=&search=&include_inactive=false" \2  --header "Authorization: Bearer {{access_token}}"

Query parameters

pageOptional
query string

1

Page number

limitOptional
query string

20

Items per page (max 100)

statusOptional
query string

Filter: unassigned | assigned

driver_idOptional
query string

Filter by driver UUID

searchOptional
query string

Partial match on route_name

include_inactiveOptional
query string

false

Include soft-deleted routes

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Routes retrieved successfully",4  "data": {5    "routes": [6      {7        "id": "route-uuid",8        "route_name": "Warehouse A → Zone 5",9        "origin_type": "warehouse",10        "origin_warehouse_id": "wh-uuid",11        "destination_type": "location",12        "destination_location": {13          "lat": 33.5,14          "lng": 44.2,15          "address": "Zone 5 Hub"16        },17        "status": "assigned",18        "is_active": true,19        "schedule_time": "08:00:00",20        "schedule_days": [21          1,22          2,23          3,24          4,25          526        ],27        "notes": null,28        "created_at": "2026-04-14T10:00:00Z",29        "driver": {30          "id": "driver-uuid",31          "full_name": "Ahmed Hassan",32          "avatar_url": "https://..."33        },34        "active_orders_count": 835      }36    ],37    "total": 1,38    "page": 1,39    "limit": 2040  }41}

Create Route

Delivery & Last-Mile / Routes
POST/delivery/routes

Create a new route. - origin_type / destination_type: warehouse | location - If type is warehouse: provide *_warehouse_id - If type is location: provide *_location as {lat, lng, address} - driver_id optional — if provided, route status becomes assigned - schedule_time, schedule_days, start_date are informational only (no backend scheduling)

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request POST "$ONDI_BASE_URL/delivery/routes" \2  --header "Authorization: Bearer {{access_token}}" \3  --header "Content-Type: application/json" \4  --header "Content-Type: application/json" \5  --data '{6  "route_name": "Warehouse A → Zone 5",7  "origin_type": "warehouse",8  "origin_warehouse_id": "wh-uuid",9  "destination_type": "location",10  "destination_location": {11    "lat": 33.5,12    "lng": 44.2,13    "address": "Zone 5 Hub"14  },15  "driver_id": "driver-uuid",16  "schedule_time": "08:00:00",17  "schedule_days": [18    1,19    2,20    3,21    4,22    523  ],24  "start_date": "2026-04-15",25  "notes": "Morning route"26}'
Request body
json
1{2  "route_name": "Warehouse A → Zone 5",3  "origin_type": "warehouse",4  "origin_warehouse_id": "wh-uuid",5  "destination_type": "location",6  "destination_location": {7    "lat": 33.5,8    "lng": 44.2,9    "address": "Zone 5 Hub"10  },11  "driver_id": "driver-uuid",12  "schedule_time": "08:00:00",13  "schedule_days": [14    1,15    2,16    3,17    4,18    519  ],20  "start_date": "2026-04-15",21  "notes": "Morning route"22}

Request body fields

route_nameExample
string

Example field from the request body.

origin_typeExample
string

Example field from the request body.

origin_warehouse_idExample
string

Example field from the request body.

destination_typeExample
string

Example field from the request body.

destination_locationExample
object

Example field from the request body.

destination_location.latExample
number

Example field from the request body.

destination_location.lngExample
number

Example field from the request body.

destination_location.addressExample
string

Example field from the request body.

driver_idExample
string

Example field from the request body.

schedule_timeExample
string

Example field from the request body.

schedule_daysExample
array<number>

Example field from the request body.

start_dateExample
string

Example field from the request body.

notesExample
string

Example field from the request body.

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Content-TypeOptional
header string

application/json

Responses

Success201Created
Response body
json
1{2  "success": true,3  "message": "Route created successfully",4  "data": {5    "id": "route-uuid",6    "route_name": "Warehouse A → Zone 5",7    "status": "assigned",8    "is_active": true,9    "created_at": "2026-04-14T10:00:00Z"10  }11}
Duplicate name409Conflict
Response body
json
1{2  "success": false,3  "message": "Route name already exists",4  "data": null5}

Get Route

Delivery & Last-Mile / Routes
GET/delivery/routes/:routeId

Get route detail including driver info, warehouse names, and current open/started session.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request GET "$ONDI_BASE_URL/delivery/routes/:routeId" \2  --header "Authorization: Bearer {{access_token}}"

Path parameters

routeIdRequired
path string

route-uuid

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route retrieved successfully",4  "data": {5    "id": "route-uuid",6    "route_name": "Warehouse A → Zone 5",7    "origin_type": "warehouse",8    "origin_warehouse": {9      "id": "wh-uuid",10      "name": "Warehouse A",11      "code": "WH-001"12    },13    "destination_type": "location",14    "destination_location": {15      "lat": 33.5,16      "lng": 44.2,17      "address": "Zone 5 Hub"18    },19    "driver": {20      "id": "driver-uuid",21      "full_name": "Ahmed Hassan",22      "avatar_url": "https://..."23    },24    "current_session": {25      "id": "session-uuid",26      "session_number": 3,27      "status": "started",28      "started_at": "2026-04-14T08:05:00Z"29    },30    "session_counts": {31      "active": 1,32      "completed": 1,33      "total": 334    },35    "status": "assigned",36    "is_active": true37  }38}

Update Route

Delivery & Last-Mile / Routes
PUT/delivery/routes/:routeId

Partial update. All fields optional. If driver_id changes, the request is rejected whenever the route has any non-terminal session (open, started, picked_up, or in_transit).

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request PUT "$ONDI_BASE_URL/delivery/routes/:routeId" \2  --header "Authorization: Bearer {{access_token}}" \3  --header "Content-Type: application/json" \4  --header "Content-Type: application/json" \5  --data '{6  "route_name": "Warehouse A → Zone 6",7  "notes": "Updated route",8  "schedule_days": [9    1,10    3,11    512  ]13}'
Request body
json
1{2  "route_name": "Warehouse A → Zone 6",3  "notes": "Updated route",4  "schedule_days": [5    1,6    3,7    58  ]9}

Path parameters

routeIdRequired
path string

route-uuid

Request body fields

route_nameExample
string

Example field from the request body.

notesExample
string

Example field from the request body.

schedule_daysExample
array<number>

Example field from the request body.

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Content-TypeOptional
header string

application/json

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route updated successfully",4  "data": {5    "id": "route-uuid",6    "route_name": "Warehouse A → Zone 6",7    "updated_at": "2026-04-14T11:00:00Z"8  }9}

Delete Route (Deactivate)

Delivery & Last-Mile / Routes
DELETE/delivery/routes/:routeId

Soft-deactivate a route (sets is_active=false). Rejected if the route has open/started sessions with active deliveries.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request DELETE "$ONDI_BASE_URL/delivery/routes/:routeId" \2  --header "Authorization: Bearer {{access_token}}"

Path parameters

routeIdRequired
path string

route-uuid

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route deactivated successfully",4  "data": null5}
Active sessions exist409Conflict
Response body
json
1{2  "success": false,3  "message": "Cannot deactivate route with active sessions that have deliveries",4  "data": null5}

Assign Driver

Delivery & Last-Mile / Routes
POST/delivery/routes/:routeId/assign-driver

Assign a driver to the route. Validates: - Driver is active with a primary vehicle - Driver has zone access for route origin and destination - Route has no non-terminal session (open, started, picked_up, in_transit) If the route has any active session, driver switching is rejected instead of transferring ownership mid-session.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request POST "$ONDI_BASE_URL/delivery/routes/:routeId/assign-driver" \2  --header "Authorization: Bearer {{access_token}}" \3  --header "Content-Type: application/json" \4  --header "Content-Type: application/json" \5  --data '{6  "driver_id": "driver-uuid"7}'
Request body
json
1{2  "driver_id": "driver-uuid"3}

Path parameters

routeIdRequired
path string

route-uuid

Request body fields

driver_idExample
string

Example field from the request body.

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Content-TypeOptional
header string

application/json

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route driver assigned successfully",4  "data": {5    "id": "route-uuid",6    "driver_id": "driver-uuid",7    "status": "assigned"8  }9}
Driver not in zone409Conflict
Response body
json
1{2  "success": false,3  "message": "Driver not allowed in route origin zone",4  "data": null5}

Unassign Driver

Delivery & Last-Mile / Routes
POST/delivery/routes/:routeId/unassign-driver

Remove the assigned driver from the route. Rejected if the route has any non-terminal session (open, started, picked_up, in_transit).

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request POST "$ONDI_BASE_URL/delivery/routes/:routeId/unassign-driver" \2  --header "Authorization: Bearer {{access_token}}"

Path parameters

routeIdRequired
path string

route-uuid

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route driver unassigned successfully",4  "data": {5    "id": "route-uuid",6    "driver_id": null,7    "status": "unassigned"8  }9}

Assign Deliveries to Route

Delivery & Last-Mile / Routes
POST/delivery/routes/:routeId/assign-deliveries

Assign deliveries to a route. Validates each delivery: - carrier_type must be internal - status must be pending - must not be in an active waybill Checks driver capacity before assigning. Creates a delivery_assignment for each delivery. Resolves existing open/started session or creates a new one. Driver is notified via BULK_DELIVERY_ASSIGNED notification.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request POST "$ONDI_BASE_URL/delivery/routes/:routeId/assign-deliveries" \2  --header "Authorization: Bearer {{access_token}}" \3  --header "Content-Type: application/json" \4  --header "Content-Type: application/json" \5  --data '{6  "delivery_ids": [7    "delivery-uuid-1",8    "delivery-uuid-2",9    "delivery-uuid-3"10  ]11}'
Request body
json
1{2  "delivery_ids": [3    "delivery-uuid-1",4    "delivery-uuid-2",5    "delivery-uuid-3"6  ]7}

Path parameters

routeIdRequired
path string

route-uuid

Request body fields

delivery_idsExample
array<string>

Example field from the request body.

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Content-TypeOptional
header string

application/json

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Deliveries assigned to route successfully",4  "data": {5    "session": {6      "id": "session-uuid",7      "session_number": 3,8      "status": "open"9    },10    "assigned_count": 311  }12}
Route unassigned409Conflict
Response body
json
1{2  "success": false,3  "message": "Route must have an assigned driver before adding deliveries",4  "data": null5}
Capacity exceeded409Conflict
Response body
json
1{2  "success": false,3  "message": "Driver does not have enough capacity for these deliveries",4  "data": null5}

Remove Deliveries from Route

Delivery & Last-Mile / Routes
POST/delivery/routes/:routeId/remove-deliveries

Remove deliveries from the route session. Only allowed if session is open or started. For each delivery: deletes the delivery_assignment record and resets delivery status to pending. Decrements driver capacity.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request POST "$ONDI_BASE_URL/delivery/routes/:routeId/remove-deliveries" \2  --header "Authorization: Bearer {{access_token}}" \3  --header "Content-Type: application/json" \4  --header "Content-Type: application/json" \5  --data '{6  "delivery_ids": [7    "delivery-uuid-1"8  ]9}'
Request body
json
1{2  "delivery_ids": [3    "delivery-uuid-1"4  ]5}

Path parameters

routeIdRequired
path string

route-uuid

Request body fields

delivery_idsExample
array<string>

Example field from the request body.

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Content-TypeOptional
header string

application/json

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Deliveries removed from route successfully",4  "data": {5    "removed_count": 16  }7}
Session picked_up409Conflict
Response body
json
1{2  "success": false,3  "message": "Cannot remove deliveries from a session that is picked_up or beyond",4  "data": null5}

List Sessions for Route

Delivery & Last-Mile / Routes
GET/delivery/routes/:routeId/sessions?status=&page=1&limit=20

Dispatcher view — paginated sessions for a route ordered newest first. Response also includes statuses matrix for the route session tabs/counts, unaffected by the active status filter.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request GET "$ONDI_BASE_URL/delivery/routes/:routeId/sessions?status=&page=1&limit=20" \2  --header "Authorization: Bearer {{access_token}}"

Path parameters

routeIdRequired
path string

route-uuid

Query parameters

statusOptional
query string

Filter: open | started | picked_up | completed | cancelled

pageOptional
query string

1

Page number (default: 1)

limitOptional
query string

20

Items per page (default: 20, max: 100)

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route sessions retrieved successfully",4  "data": {5    "sessions": [6      {7        "id": "session-uuid-2",8        "session_number": 2,9        "status": "open",10        "orders_count": 3,11        "started_at": null,12        "created_at": "2026-04-14T08:00:00Z"13      },14      {15        "id": "session-uuid",16        "session_number": 1,17        "status": "completed",18        "orders_count": 5,19        "started_at": "2026-04-13T08:00:00Z",20        "picked_up_at": "2026-04-13T08:15:00Z",21        "completed_at": "2026-04-13T14:00:00Z",22        "created_at": "2026-04-13T07:55:00Z"23      }24    ],25    "statuses": [26      {27        "status": "open",28        "label": "Open",29        "count": 130      },31      {32        "status": "started",33        "label": "Started",34        "count": 035      },36      {37        "status": "picked_up",38        "label": "Picked Up",39        "count": 040      },41      {42        "status": "completed",43        "label": "Completed",44        "count": 145      },46      {47        "status": "cancelled",48        "label": "Cancelled",49        "count": 050      }51    ],52    "total": 2,53    "page": 1,54    "limit": 2055  }56}

List Driver Route Sessions

Delivery & Last-Mile / Routes
GET/delivery/route-sessions?status=&page=1&limit=20

Driver-facing. Returns paginated sessions assigned to the authenticated driver (resolved from JWT context — no driver_id query param accepted). Ordered newest first, includes route origin/destination for each session, and returns a statuses matrix for the driver session tabs/counts unaffected by the active status filter.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request GET "$ONDI_BASE_URL/delivery/route-sessions?status=&page=1&limit=20" \2  --header "Authorization: Bearer {{access_token}}"

Query parameters

statusOptional
query string

Filter: open | started | picked_up | completed | cancelled

pageOptional
query string

1

Page number (default: 1)

limitOptional
query string

20

Items per page (default: 20, max: 100)

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route sessions retrieved successfully",4  "data": {5    "sessions": [6      {7        "id": "session-uuid",8        "session_number": 2,9        "status": "started",10        "orders_count": 4,11        "created_at": "2026-04-14T09:00:00Z",12        "route": {13          "id": "route-uuid",14          "route_name": "Warehouse A → Zone 5",15          "origin_type": "warehouse",16          "destination_type": "location",17          "destination_location": {18            "lat": 33.5,19            "lng": 44.2,20            "address": "Zone 5 Hub"21          }22        }23      }24    ],25    "statuses": [26      {27        "status": "open",28        "label": "Open",29        "count": 030      },31      {32        "status": "started",33        "label": "Started",34        "count": 135      },36      {37        "status": "picked_up",38        "label": "Picked Up",39        "count": 040      },41      {42        "status": "completed",43        "label": "Completed",44        "count": 045      },46      {47        "status": "cancelled",48        "label": "Cancelled",49        "count": 050      }51    ],52    "total": 1,53    "page": 1,54    "limit": 2055  }56}

Get Route Session Detail

Delivery & Last-Mile / Routes
GET/delivery/route-sessions/:sessionId

Returns session detail with route info and all deliveries. Accessible by the assigned driver or a dispatcher. Route origin/destination in response tells the driver where to travel. Individual delivery addresses are preserved in each delivery record.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request GET "$ONDI_BASE_URL/delivery/route-sessions/:sessionId" \2  --header "Authorization: Bearer {{access_token}}"

Path parameters

sessionIdRequired
path string

session-uuid

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route session retrieved successfully",4  "data": {5    "session": {6      "id": "session-uuid",7      "session_number": 2,8      "status": "started",9      "started_at": "2026-04-14T08:05:00Z",10      "picked_up_at": null11    },12    "route": {13      "id": "route-uuid",14      "route_name": "Warehouse A → Zone 5",15      "origin_type": "warehouse",16      "destination_type": "location",17      "destination_location": {18        "lat": 33.5,19        "lng": 44.2,20        "address": "Zone 5 Hub"21      }22    },23    "deliveries": [24      {25        "id": "del-uuid",26        "delivery_code": 1234,27        "status": "assigned",28        "unit_size": 1,29        "deliveryService": {30          "id": "service-uuid",31          "name": "Standard Delivery",32          "deliveryType": "Pickup and Delivery"33        },34        "customer": {35          "id": "cust-uuid",36          "full_name": "Sara Ahmed",37          "phone": "+9647501111111"38        }39      }40    ],41    "summary": {42      "total": 5,43      "status_breakdown": {44        "assigned": 3,45        "picked_up": 246      }47    }48  }49}

Start Session (Driver)

Delivery & Last-Mile / Routes
POST/delivery/route-sessions/:sessionId/start

Driver action. Transitions session: open → started. Sets started_at.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request POST "$ONDI_BASE_URL/delivery/route-sessions/:sessionId/start" \2  --header "Authorization: Bearer {{access_token}}"

Path parameters

sessionIdRequired
path string

session-uuid

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route session started successfully",4  "data": {5    "id": "session-uuid",6    "status": "started",7    "started_at": "2026-04-14T08:05:00Z"8  }9}
Wrong status409Conflict
Response body
json
1{2  "success": false,3  "message": "Cannot start a session with status 'picked_up'",4  "data": null5}

Pickup Session (Driver)

Delivery & Last-Mile / Routes
POST/delivery/route-sessions/:sessionId/pickup

Driver action. Transitions session: started → picked_up. Sets picked_up_at. After pickup, the session is closed for new orders. Any new assign-deliveries on this route will create a new session.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request POST "$ONDI_BASE_URL/delivery/route-sessions/:sessionId/pickup" \2  --header "Authorization: Bearer {{access_token}}"

Path parameters

sessionIdRequired
path string

session-uuid

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route session picked up successfully",4  "data": {5    "id": "session-uuid",6    "status": "picked_up",7    "picked_up_at": "2026-04-14T08:20:00Z"8  }9}

List Eligible Deliveries for Route

Delivery & Last-Mile / Routes
GET/delivery/routes/:routeId/eligible-deliveries?page=1&limit=20&search=

Returns paginated list of deliveries eligible to be assigned to this route. Eligibility criteria: - status = pending - carrier_type = internal - not already in a route session (route_session_id IS NULL)

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request GET "$ONDI_BASE_URL/delivery/routes/:routeId/eligible-deliveries?page=1&limit=20&search=" \2  --header "Authorization: Bearer {{access_token}}"

Path parameters

routeIdRequired
path string

route-uuid

Query parameters

pageOptional
query string

1

Page number

limitOptional
query string

20

Items per page (max 100)

searchOptional
query string

Search by delivery_code or external_reference_id

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Eligible deliveries retrieved successfully",4  "data": {5    "deliveries": [6      {7        "id": "del-uuid",8        "delivery_code": 1865,9        "barcode": "BAR1865",10        "external_reference_id": "ORD-001",11        "status": "pending",12        "unit_size": 1,13        "pickup_location": {14          "address": "Erbil, 60m Street"15        },16        "delivery_location": {17          "address": "Sulaymaniyah, Salim St"18        },19        "customer": {20          "id": "cust-uuid",21          "full_name": "Ahmad Karimi",22          "phone": "+9647501111111"23        }24      }25    ],26    "total": 24,27    "page": 1,28    "limit": 2029  }30}

Cancel Session (Dispatcher)

Delivery & Last-Mile / Routes
POST/delivery/route-sessions/:sessionId/cancel

Dispatcher action. Cancels session if it is open or started. Rejected for picked_up/completed sessions. For each non-terminal delivery: deletes the assignment record and resets delivery to pending. Decrements driver capacity. Notifies driver.

Send a bearer token in the Authorization header for an authenticated OnDi user session.
Request
curl
1curl --request POST "$ONDI_BASE_URL/delivery/route-sessions/:sessionId/cancel" \2  --header "Authorization: Bearer {{access_token}}"

Path parameters

sessionIdRequired
path string

session-uuid

Headers

AuthorizationOptional
header string

Bearer {{access_token}}

Responses

Success200OK
Response body
json
1{2  "success": true,3  "message": "Route session cancelled successfully",4  "data": {5    "id": "session-uuid",6    "status": "cancelled",7    "cancelled_at": "2026-04-14T09:00:00Z"8  }9}
Already picked up409Conflict
Response body
json
1{2  "success": false,3  "message": "Cannot cancel a session that has been picked up — driver already has the orders",4  "data": null5}