Pathao Commerce Instant Delivery API Documentation
Summary
Pathao API uses OAuth 2.0. There are 2 requests being sent here. 1st request is for getting the access token. This access token should be saved in the database (or any persistent store) for future use. 2nd request is for creating a new order. This uses the access token previously saved.
For understanding these APIs, we are providing Sandbox/Test Environment's Credentials here. And later you can easily integrate for Production/Live Environment by using your Live Credentials.
Generate Production Access TokenNow you can easily integrate Pathao Commerce API's into your website.
Client ID
Client Secret
Sandbox/Test Environment Credentials
| Field Name | Value |
|---|---|
| base_url | https://commerce-sandbox-api.pathao.com |
| client_id | dev_764e838bb50d166c0d4f2c9a |
| client_secret | XnRzVASbb9RtHBfltCbYT9QfEiD-i_WznkKbzsirAV0 |
Production/Live Environment
| Field Name | Value |
|---|---|
| base_url | https://commerce-api.pathao.com |
| client_id | You can see client_id from merchant api credentials section |
| client_secret | You can see client_secret from merchant api credentials section. |
Authorization Token
POSTEndpoint:
/api/v1/auth/generate-access-tokenGenerate a new API access token using the client credentials. This token is required for all subsequent API requests.
curl \
--location '{{base_url}}/api/v1/auth/generate-access-token' \
--header 'Content-Type: application/json' \
--data '{
"client_id": "Your Client Id",
"client_secret": "Your Client Secret"
}'Success Response
200{
"data": {
"access_token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ1c2VyX2lkwiYnVzaW5lc3NfaWQiOjgsImJ19nZW5liOnRydWUsImNsaWVudF...",
"expires_at": "2026-05-05T17:03:31.740738+06:00"
}
}
Response Data
| Field Name | Field Type | Description |
|---|---|---|
| data | object | Wrapper object containing token payload. |
| data.access_token | string | Bearer token used in `Authorization` header for all protected endpoints. |
| data.expires_at | string | Token expiration timestamp with timezone offset. |
Parcel Estimation
POSTEndpoint:
/api/v1/ondemand/parcels/estimationReturns an estimated delivery cost and a session ID (`sid`). You must call this before Parcel Create; the `sid` is valid for a limited time (see `estimation_ttl`). Use the response to show the customer the fare and to create the order.
curl \
--location '{{base_url}}/api/v1/ondemand/parcels/estimation?lang=en' \
--header 'Authorization: Bearer {{access_token}}' \
--header 'Content-Type: application/json' \
--data '{
"pickup": {
"address": "31, Road 7, Section 12",
"address_notes": "",
"pickup_notes": "",
"house": "",
"latitude": 23.8244683,
"longitude": 90.3737437,
"name": "Imran",
"parcel_type": 104,
"total_item_value": 100,
"phone_number": "015XXXXXX49",
"items": [
{
"name": "Pizza",
"ref_id": "xyz",
"quantity": 1,
"size": "small",
"dimensions": "120,20,30",
"weight": 120,
"price": 900,
"description": ""
}
],
"pickup_ready_at": 1773209029,
"pickup_deadline_at": 1773219029
},
"receiver": [
{
"address": "Mirpur 12 Bus Stand",
"address_notes": "",
"delivery_notes": "",
"house": "",
"total_item_value": 100,
"latitude": 23.82937676656,
"longitude": 90.363920107484,
"name": "Imran",
"parcel_type": 104,
"phone_number": "015XXXXXX49",
"road": "Begum Rokeya Avenue",
"items": [
{
"name": "Pizza",
"ref_id": "xyz",
"quantity": 1,
"size": "small",
"dimensions": "120,20,30",
"weight": 120,
"price": 900,
"description": ""
}
],
"dropoff_ready_at": 1773219029,
"dropoff_deadline_at": 1773229029
}
],
"external_store_id": "123",
"total_value": 1200,
"is_creator_receiver": false,
"is_payment_on_delivery": true,
"slug": "84cf4c66262f53771bd547df"
}'Request Parameters
| Field Name | Field Type | Required | Description |
|---|---|---|---|
| pickup.address | string | Yes | Full pickup address. |
| pickup.latitude | float | Yes | Pickup location latitude (WGS84). |
| pickup.longitude | float | Yes | Pickup location longitude (WGS84). |
| pickup.name | string | Yes | Sender or contact name at pickup. |
| pickup.phone_number | string | Yes | Contact phone at pickup. |
| pickup.parcel_type | integer | Yes | Category ID from Parcel Types. |
| pickup.house | string | No | House or building number. |
| pickup.address_notes | string | No | Extra address or landmark details. |
| pickup.pickup_notes | string | No | Instructions for the courier at pickup. |
| pickup.items | array | No | Line items included in the parcel. |
| pickup.items[].name | string | No | Item name. |
| pickup.items[].ref_id | string | No | Your item reference ID (SKU / internal ID). |
| pickup.items[].quantity | integer | No | Quantity. |
| pickup.items[].size | string | No | Size descriptor (e.g. small, medium). |
| pickup.items[].dimensions | string | No | Dimensions in cm as length,width,height. |
| pickup.items[].weight | number | No | Weight in grams. |
| pickup.items[].price | number | No | Unit price. |
| pickup.items[].description | string | No | Item description (optional). |
| pickup.pickup_ready_at | integer | No | Pickup ready time as Unix UTC timestamp (seconds). |
| pickup.pickup_deadline_at | integer | No | Latest acceptable pickup time as Unix UTC timestamp (seconds). |
| receiver | array | Yes | One or more delivery stops. |
| receiver[].address | string | Yes | Full delivery address. |
| receiver[].latitude | float | Yes | Delivery location latitude. |
| receiver[].longitude | float | Yes | Delivery location longitude. |
| receiver[].name | string | Yes | Recipient name. |
| receiver[].phone_number | string | Yes | Recipient phone number. |
| receiver[].parcel_type | integer | Yes | Category ID from Parcel Types. |
| receiver[].total_item_value | number | No | Declared value for this stop. |
| receiver[].road | string | No | Road or street name. |
| receiver[].house | string | No | House or flat number. |
| receiver[].address_notes | string | No | Additional address details. |
| receiver[].delivery_notes | string | No | Instructions for the courier at delivery. |
| receiver[].items | array | No | Line items for this stop (same structure as pickup.items). |
| receiver[].dropoff_ready_at | integer | No | Dropoff ready time as Unix UTC timestamp (seconds). |
| receiver[].dropoff_deadline_at | integer | No | Latest acceptable delivery time as Unix UTC timestamp (seconds). |
| external_store_id | string | No | Your store or location identifier. |
| total_value | number | No | Overall declared value of the shipment. |
| is_creator_receiver | bool | No | default value is false means sender |
| slug | string | No | Slug of payout method. Required if is_payment_on_delivery true. |
Success Response
200{
"status": true,
"data": {
"sid": "1f705dd5-5417-4fd2-9bd5-ff4e15644094",
"is_cod_active": true,
"server_time": 1773209029,
"estimation_ttl": 300,
"total_value": 100,
"sender_collectable_amount": 1170,
"sender_payout_fee": 0,
"sender_cod_service_fee": 30,
"service_options": [
{
"id": 1,
"name": "Instant Delivery",
"distance": 4584,
"polyline": "eelpCacrfP...",
"charge": 114.26,
"discount": 0,
"charge_after_discount": 114.26,
"dropoff_eta": 3000,
"pickup_eta": 200,
"dropoff_deadline": 1773209029
},
{
"id": 2,
"name": "4-Hour Delivery",
"distance": 4584,
"polyline": "eelpCacrfP...",
"charge": 114.26,
"discount": 0,
"charge_after_discount": 114.26,
"dropoff_eta": 3000,
"pickup_eta": 200,
"dropoff_deadline": 1773209029
},
{
"id": 3,
"name": "Same Day Delivery",
"distance": 4584,
"polyline": "eelpCacrfP...",
"charge": 114.26,
"discount": 0,
"charge_after_discount": 114.26,
"dropoff_eta": 3000,
"pickup_eta": 200,
"dropoff_deadline": 1773209029
}
]
}
}
Response Data
| Field Name | Field Type | Description |
|---|---|---|
| status | boolean | Whether the estimation request succeeded. |
| data | object | Wrapper object containing the estimation payload. |
| data.sid | string | Session ID; required in the next Create Parcel request. |
| data.is_cod_active | boolean | Whether cash-on-delivery is available and enabled. |
| data.sender_collectable_amount | float | Collectable amount of sender for payment on delivery order |
| data.sender_payout_fee | float | Fee for payout of payment on delivery order |
| data.sender_cod_service_fee | float | Payment on delivery service fee taken by pathao |
| data.server_time | integer | Server timestamp (Unix seconds). |
| data.estimation_ttl | integer | Seconds until this estimate expires (e.g. 300). |
| data.total_value | number | Declared total value from the request. |
| data.service_options | array | Available service options (delivery speed tiers) for this route. |
| data.service_options[].id | integer | Service option identifier. |
| data.service_options[].name | string | Display name (e.g. Instant Delivery, 4-Hour Delivery). |
| data.service_options[].distance | integer | Route distance in meters for this option. |
| data.service_options[].polyline | string | Encoded route polyline. |
| data.service_options[].charge | float | Delivery charge before discounts. |
| data.service_options[].discount | float | Discount applied to this option. |
| data.service_options[].charge_after_discount | float | Final charge after any discounts. |
| data.service_options[].dropoff_eta | integer | Estimated time to dropoff (seconds). |
| data.service_options[].pickup_eta | integer | Estimated time to pickup (seconds). |
| data.service_options[].dropoff_deadline | integer | Latest dropoff time as Unix UTC timestamp (seconds). |
Parcel Categories
GETEndpoint:
/api/v1/ondemand/parcels/categoriesReturns all supported parcel categories (e.g. Documents, Clothes, Gifts). Use the `id` of each category as `parcel_type` in Parcel Estimation and Create Parcel requests.
curl \
--location '{{base_url}}/api/v1/ondemand/parcels/categories' \
--header 'Authorization: Bearer {{access_token}}'Success Response
200{
"categories": [
{
"id": 101,
"name": "Homemade food",
"description": "Home cooked food",
"icon": "/service/icons/parcel/ic_Homemade Food.png",
"limit": 2500
},
{
"id": 102,
"name": "Clothes",
"description": "Fold neatly and pack securely",
"icon": "/service/icons/parcel/ic_Cloths.png",
"limit": 2500
},
{
"id": 103,
"name": "Documents",
"description": "No Passport or bank cheques",
"icon": "/service/icons/parcel/ic_Documents.png",
"limit": 0
},
{
"id": 104,
"name": "Gifts",
"description": "Flowers, cards, chocolates, and others",
"icon": "/service/icons/parcel/ic_Gifts.png",
"limit": 2500
},
{
"id": 105,
"name": "Cosmetics",
"description": "Makeup, skincare, or hygiene products. Ensure liquids are tightly sealed and packed to avoid leaks",
"icon": "/service/icons/parcel/ic_Cosmetics.png",
"limit": 2500
},
{
"id": 106,
"name": "Medicine",
"description": "Prescription or over-the-counter medicines, securely sealed with clear labeling. No illegal or prohibited drugs allowed",
"icon": "/service/icons/parcel/ic_Medicine.png",
"limit": 2500
},
{
"id": 107,
"name": "Accessories",
"description": "Watches, jewellery, bags, shoes etc, comment if fragile",
"icon": "/service/icons/parcel/ic_Accessories.png",
"limit": 2500
},
{
"id": 108,
"name": "Perishable",
"description": "Fruits, vegetables, fishes, frozen foods etc",
"icon": "/service/icons/parcel/ic_Perishable Goods.png",
"limit": 2500
},
{
"id": 109,
"name": "Electronics",
"description": "Bubble-wrapped, comment if fragile",
"icon": "/service/icons/parcel/ic_Electronics.png",
"limit": 2500
},
{
"id": 110,
"name": "Other Items",
"description": "Art supplies, toys, stationery, small tools, or household items.",
"icon": "/service/icons/parcel/ic_Other Items.png",
"limit": 2500
}
]
}
Response Data
| Field Name | Field Type | Description |
|---|---|---|
| categories | array | List of parcel category objects |
| categories[] | object | Category object |
| categories[].id | integer | Category ID; use this as parcel_type in estimation and create requests |
| categories[].name | string | Display name of the category |
| categories[].description | string | Packing or handling guidelines for this category |
| categories[].icon | string | URL path to the category icon image |
| categories[].limit | integer | Liability limit in BDT; 0 means no coverage (e.g. Documents) |
Parcel Create
POSTEndpoint:
/api/v1/ondemand/parcelsCreates a new parcel delivery order. Requires a valid `sid` from Parcel Estimation. Returns the parcel `hashed_id` and tracking URL for status updates and tracking.
curl \
--location '{{base_url}}/api/v1/ondemand/parcels?lang=en' \
--header 'Authorization: Bearer {{access_token}}' \
--header 'Content-Type: application/json' \
--data '{
"sid": "1f705dd5-5417-4fd2-9bd5-ff4e15644094",
"is_payment_on_delivery": true,
"slug": "84cf4c66262f53771bd547df",
"service_option_id": 1,
"pickup": {
"address": "31, Road 7, Section 12",
"address_notes": "",
"pickup_notes": "",
"house": "",
"latitude": 23.8244683,
"longitude": 90.3737437,
"name": "Imran",
"parcel_type": 104,
"total_item_value": 100,
"phone_number": "015XXXXXX49",
"items": [
{
"name": "Pizza",
"ref_id": "xyz",
"quantity": 1,
"size": "small",
"dimensions": "120,20,30",
"weight": 120,
"price": 900,
"description": ""
}
],
"pickup_ready_at": 1773209029,
"pickup_deadline_at": 1773219029
},
"receiver": [
{
"address": "Mirpur 12 Bus Stand",
"address_notes": "",
"delivery_notes": "",
"house": "",
"total_item_value": 100,
"latitude": 23.82937676656,
"longitude": 90.363920107484,
"name": "Imran",
"parcel_type": 104,
"phone_number": "015XXXXXX49",
"road": "Begum Rokeya Avenue",
"items": [
{
"name": "Pizza",
"ref_id": "xyz",
"quantity": 1,
"size": "small",
"dimensions": "120,20,30",
"weight": 120,
"price": 900,
"description": ""
}
],
"dropoff_ready_at": 1773219029,
"dropoff_deadline_at": 1773229029
}
],
"external_store_id": "123",
"total_value": 1200,
"external_ref_id": "xyz",
"will_pay": "receiver",
"is_creator_receiver": false
}'Request Parameters
| Field Name | Field Type | Required | Description |
|---|---|---|---|
| sid | string | Yes | Session ID from Parcel Estimation; must not be expired. |
| service_option_id | integer | Yes | Selected service option id from the estimation response. |
| is_payment_on_delivery | boolean | No | Whether payment is collected at delivery (e.g. COD). |
| slug | string | No | Slug of payout method. Required if is_payment_on_delivery true. |
| external_store_id | string | No | Your store or location identifier. |
| external_ref_id | string | No | Your own reference ID for the order. |
| total_value | number | Yes | Overall declared value of the shipment. |
| is_creator_receiver | bool | No | Default is false (creator is sender). Set true when creator is receiver. |
| pickup.address | string | Yes | Full pickup address. |
| pickup.latitude | float | Yes | Pickup location latitude (WGS84). |
| pickup.longitude | float | Yes | Pickup location longitude (WGS84). |
| pickup.name | string | Yes | Sender or contact name at pickup. |
| pickup.phone_number | string | Yes | Contact phone at pickup. |
| pickup.parcel_type | integer | Yes | Category ID from Parcel Types. |
| pickup.house | string | No | House or building number. |
| pickup.address_notes | string | No | Extra address or landmark details. |
| pickup.pickup_notes | string | No | Instructions for the courier at pickup. |
| pickup.items | array | No | Line items included in the parcel. |
| pickup.total_item_value | number | No | Total aggregated value of parcel items. |
| receiver | array | Yes | One or more delivery stops. |
| receiver[].address | string | Yes | Full delivery address. |
| receiver[].latitude | float | Yes | Delivery location latitude. |
| receiver[].longitude | float | Yes | Delivery location longitude. |
| receiver[].name | string | Yes | Recipient name. |
| receiver[].phone_number | string | Yes | Recipient phone number. |
| receiver[].parcel_type | integer | Yes | Category ID from Parcel Types. |
| receiver[].road | string | No | Road or street name. |
| receiver[].house | string | No | House or flat number. |
| receiver[].address_notes | string | No | Additional address details. |
| receiver[].delivery_notes | string | No | Instructions for the courier at delivery. |
| receiver[].items | array | No | Line items for this stop (same structure as pickup.items). |
| receiver[].total_item_value | number | No | Total declared value for this stop. |
| receiver[].dropoff_ready_at | integer | No | Dropoff ready time as Unix UTC timestamp (seconds). |
| receiver[].dropoff_deadline_at | integer | No | Latest acceptable delivery time as Unix UTC timestamp (seconds). |
Success Response
201{
"data": {
"hashed_id": "z1ci99jizevc",
"order_id": "4LHV2YB",
"charge": 114.26,
"payable_charge": 114.26,
"distance": 4584,
"created_at": 1773209183,
"server_time": 1773209183,
"total_value": 0,
"sender_collectable_amount": 1170,
"sender_payout_fee": 0,
"sender_cod_service_fee": 30,
"pickup": {
"pickup_eta": 200,
"pickup_ready": 1773209029,
"pickup_deadline": 1773209229
},
"receiver": [
{
"dropoff_eta": 3000,
"dropoff_ready": 1773209029,
"dropoff_deadline": 1773229029
}
],
"tracking_url": "/v1/ondemand/order/{parcel-id}"
}
}
Response Data
| Field Name | Field Type | Description |
|---|---|---|
| data.hashed_id | string | Alphanumeric parcel ID; use in Cancel Order and Order Details. |
| data.order_id | string | Human-readable order reference (e.g. for support). |
| data.charge | float | Delivery charge for this order. |
| data.payable_charge | float | Amount to be paid (after discounts). |
| data.distance | integer | Route distance in meters. |
| data.created_at | integer | Creation timestamp (Unix). |
| data.server_time | integer | Server timestamp (Unix). |
| data.total_value | number | Declared total value. |
| data.pickup.pickup_eta | integer | Estimated time to pickup. |
| data.pickup.pickup_ready | integer | When the parcel is ready for pickup (Unix UTC timestamp seconds). |
| data.pickup.pickup_deadline | integer | Latest pickup time (Unix UTC timestamp seconds). |
| data.receiver | array | Per-stop details; each may include dropoff_ready, dropoff_deadline, and dropoff_eta. |
| data.receiver[].dropoff_eta | integer | Estimated time to dropoff. |
| data.receiver[].dropoff_ready | integer | Dropoff ready time (Unix UTC timestamp seconds). |
| data.receiver[].dropoff_deadline | integer | Latest dropoff time (Unix UTC timestamp seconds). |
| data.tracking_url | string | URL for tracking the parcel. |
| data.sender_collectable_amount | float | Collectable amount of sender for payment-on-delivery orders. |
| data.sender_payout_fee | float | Fee for payout of payment-on-delivery orders. |
| data.sender_cod_service_fee | float | Payment-on-delivery service fee taken by Pathao. |
Parcel Cancellation
PATCHEndpoint:
/api/v1/ondemand/parcels/{parcel_id}/cancelUpdates a parcel's status. Use with status: "CANCELLED" to cancel an active order. The parcel must be cancellable (e.g. not already completed).
curl \
--location '{{base_url}}/api/v1/ondemand/parcels/{{parcel_id}}/cancel' \
--header 'Authorization: Bearer {{access_token}}' \
--header 'Content-Type: application/json' \
--data '{
"status": "CANCELLED",
"cancellation_reason": {
"slug": "customer-cancelled-order",
"additional_text": ""
}
}'Request Parameters
| Field Name | Field Type | Required | Description |
|---|---|---|---|
| parcel_id | string | Yes | Parcel's hashed_id from create or list (e.g. z1ci99jizkww). |
| status | string | Yes | New status; use CANCELLED to cancel the order. |
| cancellation_reason | object | No | Reason metadata for the cancellation. |
| cancellation_reason.slug | string | No | One of the cancellation reason slugs. |
| cancellation_reason.additional_text | string | No | Extra context (e.g. when slug is other). |
Success Response
200{
"parcel": {
"parcel_status": "CANCELLED"
}
}
Response Data
| Field Name | Field Type | Description |
|---|---|---|
| parcel | object | The updated parcel object. |
| parcel.parcel_status | string | Current status (e.g. CANCELLED). |
Parcel Details
GETEndpoint:
/api/v1/ondemand/parcels/{parcel_id}Returns full details for a specific parcel by its `hashed_id`. Use for active orders (e.g. tracking) or for historical orders (cancelled or completed). Response includes pickup, receiver, fare breakdown, and timestamps.
curl \
--location '{{base_url}}/api/v1/ondemand/parcels/{{parcel_id}}?user_type=user&localization=en' \
--header 'Authorization: Bearer {{access_token}}'Request Parameters
| Field Name | Field Type | Required | Description |
|---|---|---|---|
| parcel_id | string | Yes | Parcel's hashed_id (e.g. z1ci99jizkx7). |
| user_type | string | No | Actor type for the request. |
| localization | string | No | Language for category names and disclaimer text. |
Success Response
200{
"parcel": {
"hashed_id": "z1ci99jizevc",
"order_id": "4LHV2YB",
"parcel_status": "CANCELLED",
"charge": 114.26,
"distance": 4584,
"duration": 632,
"is_paid": 0,
"created_at": 1777548230,
"accepted_at": 1777548350,
"picked_at": 1777551413,
"started_at": 1777551416,
"completed_at": 1777551425,
"pickup": {
"address": "31, Road 7, Section 12",
"address_notes": "",
"delivery_notes": "",
"house": "",
"latitude": 23.8244683,
"longitude": 90.3737437,
"name": "Imran",
"parcel_type": 104,
"phone_number": "015XXXXXX49",
"items": [
{
"name": "Pizza",
"ref_id": "xyz",
"quantity": 1,
"size": "small",
"dimensions": "120,20,30",
"weight": 120,
"price": 900,
"description": ""
}
],
"total_item_value": 1200,
"pickup_ready_at": 1773209029,
"pickup_deadline_at": 1773219029
},
"receiver": [
{
"address": "Mirpur 12 Bus Stand",
"address_notes": "",
"delivery_notes": "",
"house": "",
"latitude": 23.82937676656,
"longitude": 90.363920107484,
"name": "Imran",
"parcel_type": 104,
"phone_number": "015XXXXXX49",
"road": "Begum Rokeya Avenue",
"items": [
{
"name": "Pizza",
"ref_id": "xyz",
"quantity": 1,
"size": "small",
"dimensions": "120,20,30",
"weight": 120,
"price": 900,
"description": ""
}
],
"total_item_value": 1200,
"dropoff_ready_at": 1773219029,
"dropoff_deadline_at": 1773229029
}
],
"rider": {
"name": "asibul H Hasan",
"number": "01767191651",
"profile_picture": "/uploads/img/profile/7PqrFI1722490453.png",
"type": "bike",
"registration_number": "DHK METRO HA 55-5956"
},
"support_number": "09678100800",
"pickup_proof_img": "/assets/abc-72960e8f.jpg",
"dropoff_proof_img": "/assets/bcd-b056ca09.jpg",
"sender_collectable_amount": 1170,
"sender_payout_fee": 0,
"sender_cod_service_fee": 30
}
}
Response Data
| Field Name | Field Type | Description |
|---|---|---|
| parcel.hashed_id | string | Alphanumeric parcel ID used in subsequent API calls. |
| parcel.order_id | string | Human-readable order reference. |
| parcel.parcel_status | string | Current parcel status (e.g. PENDING, ACCEPTED, CANCELLED, COMPLETED). |
| parcel.charge | float | Delivery charge. |
| parcel.distance | integer | Route distance in meters. |
| parcel.duration | integer | Estimated or actual duration in seconds. |
| parcel.is_paid | integer | Payment status (0/1). |
| parcel.created_at | integer | Creation timestamp (Unix seconds). |
| parcel.accepted_at | integer | null | When a rider accepted the order (Unix seconds). |
| parcel.picked_at | integer | null | When the parcel was picked up (Unix seconds). |
| parcel.started_at | integer | null | When the rider started the journey (Unix seconds). |
| parcel.completed_at | integer | null | When delivery was completed (Unix seconds). |
| parcel.pickup | object | Pickup details (address, contact, coordinates, items). |
| parcel.pickup.address | string | Full pickup address. |
| parcel.pickup.latitude | float | Pickup latitude. |
| parcel.pickup.longitude | float | Pickup longitude. |
| parcel.pickup.name | string | Pickup contact name. |
| parcel.pickup.phone_number | string | Pickup contact phone number. |
| parcel.pickup.parcel_type | integer | Category ID. |
| parcel.pickup.items | array | Items included in the pickup payload. |
| parcel.receiver | array | Receiver stop(s) with address, contact, items, and time windows. |
| parcel.receiver[].dropoff_ready_at | integer | Dropoff ready time (Unix seconds). |
| parcel.receiver[].dropoff_deadline_at | integer | Latest acceptable dropoff time (Unix seconds). |
| parcel.rider | object | Assigned rider info (may be absent until assigned). |
| parcel.rider.name | string | Rider name. |
| parcel.rider.number | string | Rider phone number. |
| parcel.rider.profile_picture | string | Rider profile picture path or URL. |
| parcel.rider.type | string | Vehicle type (e.g. bike). |
| parcel.rider.registration_number | string | Vehicle registration number. |
| parcel.support_number | string | Customer support phone number. |
| parcel.pickup_proof_img | string | Pickup proof image URL (if available). |
| parcel.dropoff_proof_img | string | Dropoff proof image URL (if available). |
| parcel.sender_collectable_amount | float | Collectable amount of sender for payment on delivery order |
| parcel.sender_payout_fee | float | Fee for payout of payment on delivery order |
| parcel.sender_cod_service_fee | float | Payment on delivery service fee taken by pathao |
Create Payout Method
POSTEndpoint:
/api/v1/ondemand/parcels/payout-methodsCreates a new payout method(bkash) for a parcel.
curl \
--location '{{base_url}}/api/v1/ondemand/parcels/payout-methods' \
--header 'Authorization: Bearer {{access_token}}' \
--header 'Content-Type: application/json' \
--data '{
"payout_method": "BKASH",
"account_type": "PERSONAL",
"account_number": "015XXXXXX49"
}'Request Parameters
| Field Name | Field Type | Required | Description |
|---|---|---|---|
| payout_method | string | Yes | Provider identifier. Currently only BKASH is supported. |
| account_type | string | Yes | Type of the payout account (e.g. PERSONAL, BUSINESS). |
| account_number | string | Yes | Account number for the payout method. |
Success Response
201{
"payout_method": "BKASH",
"account_type": "PERSONAL",
"masked_number": "015XXXXXX49",
"slug": "84cf4c66262f53771bd547df",
"is_default": true
}
Response Data
| Field Name | Field Type | Description |
|---|---|---|
| payout_method | string | The provider identifier. |
| account_type | string | The account type (PERSONAL or MERCHANT). |
| masked_number | string | The account number. |
| slug | string | Unique identifier for the created payout method; use in Update and Delete. |
| is_default | boolean | true if this is the user’s first (and thus default) payout method. |
Get Payout Methods
GETEndpoint:
/api/v1/ondemand/parcels/payout-methodsReturns the user’s saved payout methods (filtered to city/country-allowed methods) along with any additional payout options not yet added.
curl \
--location '{{base_url}}/api/v1/ondemand/parcels/payout-methods?lang=en' \
--header 'Authorization: Bearer {{access_token}}'Request Parameters
| Field Name | Field Type | Required | Description |
|---|---|---|---|
| lang | string | No | Language for localized response text (en | bn | ne). |
| from_portal | bool | No | Whether the request originated from the commerce portal. |
Success Response
200{
"payout_methods": [
{
"name": "Bkash",
"method": "BKASH",
"account_type": "PERSONAL",
"account_type_spec": {
"merchant": {
"account_number_min_length": 10,
"account_number_max_length": 10
},
"personal": {
"account_number_min_length": 11,
"account_number_max_length": 11
}
},
"masked_number": "01767191651",
"slug": "84cf4c66262f53771bd547df",
"icon": "/assets/rebranded-pathao-pay-ic-e8c46d37.png",
"notes": {
"icon": "/assets/famicons-flash-ic-9eba33b3.png",
"text": [
"Instant transfer",
"No charges"
],
"text_color": "#025BE8"
},
"is_default": true
}
],
"available_options": []
}
Response Data
| Field Name | Field Type | Description |
|---|---|---|
| payout_methods | array | User’s saved and active payout methods, filtered to city/country-allowed methods. |
| payout_methods[].name | string | Display name of the provider (from config). |
| payout_methods[].method | string | Payout method identifier (BKASH, NAGAD, PATHAO_PAY). |
| payout_methods[].account_type | string | Account type: PERSONAL or MERCHANT. |
| payout_methods[].account_type_spec | object | Map of account types to their number length constraints. |
| payout_methods[].account_type_spec.merchant.account_number_min_length | integer | Minimum account number length for MERCHANT accounts. |
| payout_methods[].account_type_spec.merchant.account_number_max_length | integer | Maximum account number length for MERCHANT accounts. |
| payout_methods[].account_type_spec.personal.account_number_min_length | integer | Minimum account number length for PERSONAL accounts. |
| payout_methods[].account_type_spec.personal.account_number_max_length | integer | Maximum account number length for PERSONAL accounts. |
| payout_methods[].masked_number | string | Masked account/mobile number. |
| payout_methods[].slug | string | Unique identifier for this payout method; use in Update and Delete. |
| payout_methods[].icon | string | URL to the provider icon. |
| payout_methods[].notes | object | Informational notes about this method. |
| payout_methods[].notes.icon | string | Icon identifier for the note (e.g. "info"). |
| payout_methods[].notes.text | array | Localized note strings (follows lang). |
| payout_methods[].notes.text_color | string | Hex color for note text. |
| payout_methods[].is_default | boolean | Whether this is the user’s default payout method. |
| available_options | array | Payout methods the user has not yet added, available in their city/country. |
| available_options[].name | string | Display name. |
| available_options[].method | string | Payout method identifier. |
| available_options[].icon | string | URL to the provider icon. |
| available_options[].notes | object | Informational notes (same structure as payout_methods[].notes). |
| available_options[].account_type | object | Map of supported account types to number length constraints. |
Update Payout Method
PATCHEndpoint:
/api/v1/ondemand/parcels/payout-methods/{slug}Sets a payout method as the user’s default. The previously default method is automatically unset. Only the make_default action is supported.
curl \
--location \
--request PATCH '{{base_url}}/api/v1/ondemand/parcels/payout-methods/{{slug}}?lang=en' \
--header 'Authorization: Bearer {{access_token}}' \
--header 'Content-Type: application/json' \
--data '{
"make_default": true
}'Request Parameters
| Field Name | Field Type | Required | Description |
|---|---|---|---|
| slug | string | Yes | Payout method slug from Create or Get Payout Methods. |
| lang | string | No | Language for localized response text (en | bn | ne). |
| make_default | boolean | Yes | Must be true. Sets this method as the default. |
Success Response
200{
"payout_method": "BKASH",
"account_type": "PERSONAL",
"masked_number": "015XXXXXX49",
"slug": "84cf4c66262f53771bd547df",
"is_default": true
}
Response Data
| Field Name | Field Type | Description |
|---|---|---|
| payout_method | string | The provider identifier. |
| account_type | string | The account type. |
| masked_number | string | The (masked) account number. |
| slug | string | The payout method slug. |
| is_default | boolean | Always true after a successful update. |
Delete Payout Method
DELETEEndpoint:
/api/v1/ondemand/parcels/payout-methods/{slug}Deletes (deactivates) a payout method. If the deleted method was the default, the next remaining method is automatically promoted to default.
curl \
--location \
--request DELETE '{{base_url}}/api/v1/ondemand/parcels/payout-methods/{{slug}}' \
--header 'Authorization: Bearer {{access_token}}'Request Parameters
| Field Name | Field Type | Required | Description |
|---|---|---|---|
| slug | string | Yes | Payout method slug from Create or Get Payout Methods. |
Success Response
200{
"message": "payout method deleted successfully"
}
Response Data
| Field Name | Field Type | Description |
|---|---|---|
| message | string | Confirmation of successful deletion. |