DiDi Delivery courier trip and payout data API
DiDi Delivery: Deliver & Earn is DiDi Global's courier app for DiDi Food, used by independent riders who pick up restaurant orders and drop them off on foot, by bicycle or by scooter. Couriers create an account with a mobile number, upload identification, and complete an in-person check at a DiDi Courier Center before they can go online and accept jobs. Once signed in they work from a home that lists available deliveries, open a live job for pickup and drop-off, review trip income after each hand-off, and cash out earnings through DiDi Pay and the in-app wallet. The Play listing is live for Mexico and Chile among other Latin American DiDi Food cities; the app holds a 3.0 rating from 92,942 reviews. Riders in those markets often run it next to Soy Rappi and Uber Eats for the same food-delivery shifts.
Pickup takeInfo lists shopName, shopAddress and cashAdvances; drop-off SendInfo carries customerName, customerAddress and cashReceivable, with isPhoneProtect on the customer number. Rider profile wire names include ID, realname, phone, workType and cityID. Wallet accountSection hangs balance next to kycStatus, fullKycStatus and bound cardNum; the balance-detail snapshot adds totalBalance, totalEarning and cashback, while statement rows keep transId, transDate and amountText.
A cash-out quote returns channelName, inputAmount and commissionAmount before canWithdraw and availableBalance update. The withdraw profile carries legal name and idNo; progress rows expose withdrawId, bankCard and predictionTime. Fleet boards overlay the live pickup; tax tools reconcile statement lines; payout desks settle on bindCard bank rows. openData Studio turns those fields into callable open data.
Screenshots
API surface
The endpoints and request/response examples below are reconstructed from the app's interface — illustrative, not a live capture.
Send login verification code
POST
/v1/didi-food/session/otpopendataSends an SMS or email one-time code for courier sign-in; returns errno plus prompt and voiceSupport.
Auth: None (starts login). Body carries cell or email plus code_type; BaseParam adds country_id, country_calling_code, canonical_country_code, appid, role, lang.
- cell
- code_type
- os_type
- country_id
- country_calling_code
- canonical_country_code
- api_version
- app_version
- lang
- errno
- error
- traceId
- prompt
- voiceSupport
POST /v1/didi-food/session/otp HTTP/1.1 Content-Type: application/json { "cell": "5215512345678", "code_type": 1, "os_type": "android", "country_id": 52, "country_calling_code": "+52", "canonical_country_code": "MX", "api_version": "1.0.2", "app_version": "2.2.78", "lang": "es-MX" }{ "errno": 0, "error": "", "traceId": "tr_9c81e2b0", "code_type": 1, "prompt": "We sent a code to **5678", "voiceSupport": true }Sign in by verification code
POST
/v1/didi-food/session/verifyosintExchanges the one-time code for a passport ticket, uid, cell and countryId used by later wallet, payout and rider RPC calls.
Auth: None (issues ticket). Body carries cell, code, codeType and loginType; extra_info may set code_type.
- cell
- code
- codeType
- loginType
- extra_info
- ticket
- uid
- countryId
- callingCode
- role
- userType
- verifySessionId
- errno
- traceId
POST /v1/didi-food/session/verify HTTP/1.1 Content-Type: application/json { "cell": "5215512345678", "code": "482193", "codeType": 1, "loginType": 1, "country_id": 52, "country_calling_code": "+52", "canonical_country_code": "MX", "api_version": "1.0.2", "app_version": "2.2.78", "extra_info": { "code_type": 1 } }{ "errno": 0, "error": "", "traceId": "tr_9c81e2b0", "ticket": "tk_8f21c0a4", "uid": 1843921001, "cell": "5215512345678", "email": "", "countryId": 52, "callingCode": "+52", "role": 2, "userType": 1, "verifySessionId": "vs_44102" }Refresh passport ticket
POST
/v1/didi-food/session/renewopendataRenews the passport ticket so wallet, DiDi Pay and rider RPC sessions stay signed in without another OTP.
Auth: Existing ticket in the JSON body; optional returncell flag.
- ticket
- returncell
- errno
- uid
- cell
- countryId
- callingCode
POST /v1/didi-food/session/renew HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4", "returncell": 1, "canonical_country_code": "MX", "api_version": "1.0.2", "app_version": "2.2.78" }{ "errno": 0, "error": "", "ticket": "tk_c91e2b77", "uid": 1843921001, "cell": "5215512345678", "countryId": 52, "callingCode": "+52" }Get rider profile
POST
/v1/didi-food/courierosintLoads the signed-in courier: ID, realname, phone, workType, cityID / countyID and countryCode used on the rider home.
Auth: Login token from the verification-code sign-in as form field token.
- token
- ID
- phone
- realname
- nickname
- headImg
- countyGroupID
- countyID
- cityID
- areaID
- status
- workType
- channel
- level
- vehicleType
- countryCode
- country
- vendorCode
- isShopper
- ttsSwitch
POST /v1/didi-food/courier HTTP/1.1 Content-Type: application/x-www-form-urlencoded token=tk_8f21c0a4{ "ID": "1843921001", "phone": "5215512345678", "realname": "Maria Lopez", "nickname": "Maria", "headImg": "", "countyGroupID": "mx-cdmx", "countyID": "09000", "cityID": "51234500", "areaID": "51234501", "status": 1, "workType": 1, "channel": 1, "level": "2", "vehicleType": "bike", "countryCode": "MX", "country": "Mexico", "vendorCode": "didi_food", "isShopper": false, "ttsSwitch": true }Get trip delivery detail
POST
/v1/didi-food/jobs/{deliveryId}opendataOpens a live DiDi Food job: pickup takeInfo (shopName, shopAddress, cashAdvances) and drop-off SendInfo (customerName, cashReceivable, isPhoneProtect).
Auth: Login token from the verification-code sign-in as form field token.
- token
- deliveryId
- takeInfo
- orderIndex
- shopName
- shopAddress
- shopPhone
- cashAdvances
- isShopPhoneProtect
- customerName
- customerPhone
- customerPoiName
- customerAddress
- customerPoiAddress
- cashReceivable
- hideCustomerAddress
- isPhoneProtect
- name
- currency
- fee
- desc
POST /v1/didi-food/jobs/{deliveryId} HTTP/1.1 Content-Type: application/x-www-form-urlencoded token=tk_8f21c0a4&deliveryId=dl_7f21c0a4{ "takeInfo": { "orderIndex": "1", "shopName": "Tacos El Guero", "shopAddress": "Av. Insurgentes 120", "shopPhone": "5551230000", "cashAdvances": "0.00", "isShopPhoneProtect": 1 }, "sendInfo": { "customerName": "Ana", "customerPhone": "5559870000", "customerPoiName": "Depto 4B", "customerAddress": "Calle Reforma 88", "customerPoiAddress": "Calle Reforma 88", "cashReceivable": "128.50", "hideCustomerAddress": 0, "isPhoneProtect": 1 }, "fee": { "name": "Delivery fee", "currency": "MXN", "fee": 28.5, "desc": "Base + distance" } }Get hot-zone order forecast
POST
/v1/didi-food/demand/forecastopendataReturns the order-forecast widget: refreshTime plus columnList rows of num and mark for the hot-zone chart.
Auth: Login token from the verification-code sign-in as form field token.
- token
- defaultInfo
- refreshTime
- columnList
- num
- mark
POST /v1/didi-food/demand/forecast HTTP/1.1 Content-Type: application/x-www-form-urlencoded token=tk_8f21c0a4{ "defaultInfo": {}, "refreshTime": 60, "columnList": [ { "num": 12.0, "mark": 1 }, { "num": 18.0, "mark": 0 } ] }Query courier wallet home balances
POST
/v1/didi-food/walletopenbankingLoads the wallet home snapshot: accountBalance.balance, kycStatus / fullKycStatus, and bound bankCard.cardNum.
Auth: Passport ticket from the verification-code sign-in call, sent as ticket in the JSON body.
- ticket
- errno
- errmsg
- data
- channelId
- needFuidLogin
- accountSection
- accountBalance
- balance
- title
- linkUrl
- authenticationStatus
- kycStatus
- fullKycStatus
- supportFullKyc
- bankCard
- cardNum
- bhasInterest
- paySection
- financialSection
POST /v1/didi-food/wallet HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4", "canonical_country_code": "MX", "lang": "es-MX" }{ "errno": 0, "errmsg": "", "data": { "channelId": "MX_WALLET", "needFuidLogin": false, "accountSection": { "accountSectionName": "DiDi Pay", "accountBalance": { "balance": "1850.40", "title": "Available", "linkUrl": "" }, "authenticationStatus": "VERIFIED", "kycStatus": "PASS", "fullKycStatus": "PASS", "supportFullKyc": true, "bankCard": { "cardNum": "****1234", "title": "BBVA", "linkUrl": "", "redDot": "0" }, "bhasInterest": false }, "paySection": {}, "financialSection": {} } }Read account balance info
POST
/v1/didi-food/wallet/balanceopenbankingLoads the balance-detail snapshot: totalBalance / totalEarning, cashback and interests, plus withoutHistory for the empty state.
Auth: Passport ticket from the verification-code sign-in call, sent as ticket in the JSON body.
- ticket
- errno
- errmsg
- data
- totalBalance
- totalBalanceLabel
- totalBalanceTitle
- totalEarning
- totalEarningLabel
- cashback
- cashbackLabel
- interests
- interestLabel
- hasHit
- withoutHistory
- judBlockedBalance
- marketingResourceEntrance
POST /v1/didi-food/wallet/balance HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4" }{ "errno": 0, "errmsg": "", "data": { "totalBalance": 185040, "totalBalanceLabel": "$1,850.40", "totalBalanceTitle": "Available", "totalEarning": 12850, "totalEarningLabel": "$128.50", "cashback": 450, "cashbackLabel": "$4.50", "interests": 12, "interestLabel": "$0.12", "hasHit": true, "withoutHistory": false, "judBlockedBalance": { "amount": 0 }, "marketingResourceEntrance": {} } }List account statements
POST
/v1/didi-food/wallet/ledgeropenbankingReturns wallet history rows with transId, businessType, transDate and amountText for the statements screen.
Auth: Passport ticket from the verification-code sign-in call, sent as ticket in the JSON body.
- ticket
- nextIndex
- linkUrl
- errno
- statement
- title
- transId
- transDate
- transDateTitle
- time
- businessType
- detailLink
- amountText
POST /v1/didi-food/wallet/ledger HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4", "nextIndex": 0 }{ "errno": 0, "errmsg": "", "data": { "nextIndex": 20, "linkUrl": "", "statement": [ { "title": "DiDi Food delivery", "transId": "txn_7f21c0a4", "transDate": "2026-10-03", "transDateTitle": "3 Oct", "time": 1759507200000, "businessType": "DELIVERY", "detailLink": "", "amountText": { "text": "$128.50" } } ] } }Read account KYC status
POST
/v1/didi-food/wallet/kycosintReads fullKycStatus and status that gate wallet cash-out and the Courier Center identity check.
Auth: Passport ticket from the verification-code sign-in call, sent as ticket in the JSON body.
- ticket
- errno
- errmsg
- data
- fullKycStatus
- status
POST /v1/didi-food/wallet/kyc HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4" }{ "errno": 0, "errmsg": "", "data": { "fullKycStatus": 1, "status": 1 } }Calculate manual withdraw
POST
/v1/didi-food/payouts/quoteopenfinanceQuotes a cash-out: channelName, inputAmount, oriAmount and commissionAmount before the courier confirms.
Auth: Passport ticket from the verification-code sign-in call, sent as ticket in the JSON body. Client also sends utc_offset, osChannel=Android, app_version.
- ticket
- inputAmount
- utc_offset
- osChannel
- app_version
- errno
- data
- channelName
- oriAmount
- commissionAmount
POST /v1/didi-food/payouts/quote HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4", "inputAmount": [ "500.00" ], "utc_offset": -360, "osChannel": "Android", "app_version": "2.2.78" }{ "errno": 0, "errmsg": "", "data": { "channelName": "SPEI", "inputAmount": [ "500.00" ], "oriAmount": [ "500.00" ], "commissionAmount": [ "8.50" ] } }Create manual withdraw
POST
/v1/didi-food/payoutsopenfinanceSubmits a cash-out and returns DriverWithdrawInfo: availableBalance, canWithdraw, hasBindAccount and bindCard rows.
Auth: Passport ticket from the verification-code sign-in call, sent as ticket in the JSON body.
- ticket
- inputAmount
- channelName
- errno
- data
- driverInfo
- availableBalance
- availableBalanceSplit
- realBalance
- canWithdraw
- hasBindAccount
- showTransferIn
- bindCard
- bankCode
- bankName
- cardNum
- cardStatus
- commissionFee
- withdrawMin
- withdrawMax
POST /v1/didi-food/payouts HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4", "inputAmount": [ "500.00" ], "channelName": "SPEI", "osChannel": "Android", "app_version": "2.2.78" }{ "errno": 0, "errmsg": "", "data": { "driverInfo": { "availableBalance": 135040, "availableBalanceSplit": [ "1,350.40" ], "realBalance": 135040, "realBalanceSplit": [ "1,350.40" ], "canWithdraw": true, "hasBindAccount": true, "showTransferIn": false, "bindCard": [ { "bankCode": "012", "bankName": "BBVA", "cardNum": "****1234", "cardStatus": 1, "commissionFee": 850, "commissionFeeDisplay": 8.5, "withdrawMin": 10000, "withdrawMax": 5000000, "isDefault": true } ] } } }Create DiDi Pay order
POST
/v1/didi-food/wallet/checkoutopenfinanceOpens a DiDi Pay cashier order and returns orderId, outTradeId and cashierType for the payment sheet.
Auth: Passport ticket from the verification-code sign-in call, sent as ticket in the JSON body.
- ticket
- errno
- data
- orderMetaData
- orderId
- outTradeId
- cashierType
- jumpToH5
- thirdPartyParams
- noticeInfo
- paymentPasswordInfo
POST /v1/didi-food/wallet/checkout HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4" }{ "errno": 0, "errmsg": "", "data": { "orderMetaData": { "orderId": "ord_8f21c0a4", "outTradeId": "ot_44102", "cashierType": 1, "jumpToH5": false, "thirdPartyParams": "", "noticeInfo": {}, "paymentPasswordInfo": {} } } }Query driver withdraw profile
POST
/v1/didi-food/payouts/profileosintLoads the courier's withdraw profile: legal name, idNo, fastTrackStatus and bindChannelCodeList used by the bank-account screen.
Auth: Passport ticket from the verification-code sign-in call, sent in the JSON body with utc_offset, osChannel=Android, app_version.
- ticket
- utc_offset
- osChannel
- app_version
- errno
- data
- name
- idNo
- status
- isAbnormal
- fastTrackStatus
- fastTrackStatusDesc
- freeWithdraw
- bindCardRule
- bindChannelCodeList
- isDefaultChannel
- lastWithdrawRetMsg
- withdrawGray
POST /v1/didi-food/payouts/profile HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4", "utc_offset": -360, "osChannel": "Android", "app_version": "2.2.78", "canonical_country_code": "MX" }{ "errno": 0, "errmsg": "", "data": { "name": "Maria Lopez", "idNo": "LOPM850101XXXX", "status": 1, "isAbnormal": false, "fastTrackStatus": "PASS", "fastTrackStatusDesc": "Verified", "freeWithdraw": 2, "bindCardRule": "SPEI", "bindChannelCodeList": [ "SPEI", "CLABE" ], "isDefaultChannel": true, "lastWithdrawRetMsg": "", "withdrawGray": 0 } }Query withdraw card channel status
POST
/v1/didi-food/payouts/channelsopenbankingLists bound payout channels with channelId, accountTitle, status and isDefaultChannel for the bank-account manager.
Auth: Passport ticket from the verification-code sign-in call, sent in the JSON body. Also sets caller=fintech_sdk.
- ticket
- caller
- errno
- data
- channelId
- accountTitle
- status
- isAbnormal
- isDefaultChannel
- lastWithdrawRetMsg
- withdrawGray
- icon
POST /v1/didi-food/payouts/channels HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4", "caller": "fintech_sdk", "osChannel": "Android", "app_version": "2.2.78" }{ "errno": 0, "errmsg": "", "data": [ { "channelId": "SPEI", "accountTitle": "BBVA ****1234", "status": "ACTIVE", "isAbnormal": false, "isDefaultChannel": 1, "lastWithdrawRetMsg": "", "withdrawGray": 0, "icon": "" } ] }Query withdrawal progress
POST
/v1/didi-food/payouts/{withdrawId}openfinanceTracks a cash-out by withdrawId: status, amount, commissionFee, bankName / bankCard and createTime / predictionTime timestamps.
Auth: Passport ticket from the verification-code sign-in call, sent in the JSON body with utc_offset, osChannel and app_version.
- ticket
- withdrawId
- errno
- data
- status
- amount
- amountSplit
- originalAmount
- commissionFee
- bankName
- bankCard
- withdrawMethodName
- createTime
- submitTime
- predictionTime
- finishTime
- bounceTime
- createContent
- submitContent
- finishContent
- bounceContent
- isDisplayRule
- accountErrorLink
POST /v1/didi-food/payouts/{withdrawId} HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4", "withdrawId": "wd_7f21c0a4", "osChannel": "Android", "app_version": "2.2.78" }{ "errno": 0, "errmsg": "", "data": { "withdrawId": "wd_7f21c0a4", "status": 2, "amount": "500.00", "amountSplit": [ "500.00" ], "originalAmount": "500.00", "commissionFee": "8.50", "bankName": "BBVA", "bankCard": "****1234", "withdrawMethodName": "SPEI", "createTime": 1759507200000, "submitTime": 1759507260000, "predictionTime": 1759593600000, "finishTime": 0, "bounceTime": 0, "createContent": "Requested", "submitContent": "Sent to bank", "finishContent": "", "bounceContent": "", "isDisplayRule": true, "accountErrorLink": "" } }Open driver face-verify session
POST
/v1/didi-food/kyc/face-sessionosintIssues a face-verify session id (session, bizCode) before the courier can bind a payout account.
Auth: Passport ticket from the verification-code sign-in call, sent in the JSON body. Used when open-account risk requires face verify.
- ticket
- errno
- errmsg
- data
- session
- bizCode
POST /v1/didi-food/kyc/face-session HTTP/1.1 Content-Type: application/json { "ticket": "tk_8f21c0a4", "osChannel": "Android", "app_version": "2.2.78" }{ "errno": 0, "errmsg": "", "data": { "session": "fs_9c81e2b0", "bizCode": 1001 } }
Data categories
- deliveries
- balances
- transactions
- payouts
- kyc
- identity
Where teams use this data
Live trip overlay
Dispatch tools read takeInfo.shopName / shopAddress and SendInfo.cashReceivable / customerAddress so a fleet board can show the current DiDi Food pickup and drop-off without scraping the courier screen.
Courier wallet reconciliation
Nightly jobs read accountBalance.balance plus statement transId / transDate / amountText so a fleet or tax tool can match DiDi Food payouts against its own ledger.
Cash-out ops
Payout desks consume channelName, commissionAmount and inputAmount from the calculate step, then settle on availableBalance, canWithdraw and bindCard.cardNum / bankName after create.
KYC gate for withdrawals
Compliance overlays watch kycStatus, fullKycStatus and authenticationStatus on the wallet home, plus rider ID / realname / workType, before enabling cash-out.
Frequently asked questions
How do DiDi Delivery couriers authenticate?
The app sends a one-time code to a mobile number or email, then exchanges it for a passport ticket, uid, cell and countryId. Wallet and payout calls send that ticket in the JSON body; rider RPC posts it as form field token. A refresh call renews the ticket without another OTP.
What trip fields does a live delivery expose?
A live job returns takeInfo.shopName, shopAddress, shopPhone and cashAdvances for pickup, plus SendInfo.customerName, customerAddress, cashReceivable and isPhoneProtect for drop-off. Rider home adds ID, realname, phone, workType, cityID and countryCode.
What wallet fields does the courier home expose?
The wallet home returns accountSection.accountBalance.balance, kycStatus, fullKycStatus, authenticationStatus and bankCard.cardNum. The balance-detail snapshot adds totalBalance, totalEarning and cashback. Statement history adds transId, transDate, businessType and amountText.
How does cash-out work?
A calculate step quotes channelName, inputAmount, oriAmount and commissionAmount. Creating the cash-out then returns availableBalance, canWithdraw, hasBindAccount and bindCard rows (bankCode, bankName, cardNum, withdrawMin, withdrawMax).
Apps similar to DiDi Delivery: Deliver & Earn
- Soy Rappi - Sé un repartidor — Soy Rappi is Rappi's courier app for independent Rappitenderos who deliver restaurant, grocery and other on-demand orders, and Rappi operates in Mexico and Chile among other Latin American countries.
- Uber - Driver: Drive & Deliver — Uber's driver app lets partners deliver restaurant meals, groceries and packages by car, bike, scooter or on foot, and Uber Eats lists Mexico and Chile among the countries it serves.
- PeYa Rider — PeYa Rider is PedidosYa's courier app, where riders register, choose shifts, accept orders and review payments on the Delivery Hero platform that operates in fifteen Latin American countries including Chile.
- iFood para Entregadores — iFood para Entregadores is the courier app for Brazil's iFood food-ordering platform, where partners register with identification and a bank account to deliver by bike, scooter, on foot, motorcycle or car.
- Lalamove — Lalamove is an on-demand freight and delivery platform that launched in Mexico and Brazil in 2019, matching users with motorcycle, car, van and truck drivers for point-to-point deliveries.
- DoorDash - Dasher — DoorDash's Dasher app lets independent couriers accept restaurant and retail delivery offers on their own schedule by bike, car, scooter or motorcycle.
Topics
- DiDi Delivery API
- DiDi Food courier wallet
- DiDi Pay withdraw
- DiDi Delivery trips
- takeInfo shopName
- cashReceivable
- courier KYC status
Need this app's data API integrated?
We deliver scoped integrations for any named app — from USD 500 with source-code handoff, or hosted access billed per call. Tell us the data you need.
- NDA + SOW on every engagement
- Delivery in 3–7 days
- Payment only after acceptance
- Work scoped to authorized use