eCommerce

Cash on delivery reconciliation: automating orders, couriers and finance

How to track cash held by couriers, match remittance statements to Shopify orders and build a month-end report, with the steps to automate and questions to put to your courier.

ESTASOFT
12 min read
Red cover with a white circle holding a black check mark, with the title Cash on delivery, reconciled
On this page
    On this page

      Cash on delivery looks simple until finance asks one question: how much of our money is with the couriers? Parcels were delivered last week and the cash is not in your account. Some parcels came back. A statement arrives with a total, and nobody can say which orders it covers.

      This guide is for owners and finance leads of Shopify stores that take cash on delivery in the Gulf or Iraq. It maps the loop from order to finance entry, shows where it breaks, and lists what to automate and in what order. It ends with questions for your courier about cash, because remittance terms can differ by courier and this guide has no source for any of them. Shopify facts come from pages read on 4 November 2026 and can change. Our guide to selling online in Iraq with cash on delivery covers cash on delivery in Iraq, so this one focuses on matching and money.

      The cash on delivery loop and where it breaks

      There are eight steps. Each has a typical failure.

      1. Order. Shopify treats cash on delivery as a manual payment method, so the order is unpaid and shows as Pending, and Shopify's order status page lists manual methods among the cases for that status. It breaks when cash orders carry no tag, because nobody can list them later.
      2. Dispatch. The parcel leaves with a courier and a tracking number. It breaks when the waybill number is not saved on the order. The courier's statement will use that number, and you will have nothing to match.
      3. Delivery or failure. Shopify's order filters offer delivery statuses: in transit, out for delivery, attempted delivery, delayed, failed delivery, delivered, tracking added and no status. Shopify's filter page does not say how these statuses are filled. Shopify Flow's Fulfillment event created trigger covers updates from third-party fulfillment services, and manual fulfillment events do not start it. Test with a real parcel before you rely on these statuses.
      4. Cash collected. Aramex's UAE FAQ has a short answer saying merchants can use Aramex to deliver and collect payment from buyers, and shows nothing on payout timing. The order stays unpaid in Shopify until you mark it paid. It breaks when "delivered" is read as "paid".
      5. Remittance. The courier pays in batches with a statement. It breaks when the statement uses waybill numbers and your orders use order numbers, when fees are deducted, or when a line is short.
      6. Match and mark paid. Shopify's help page describes Mark as paid as the option for when you have already received payment, and says your payment provider does not capture the amount again. It states that an order confirmation email is sent to the customer, and it warns that for a pending order paid by something other than a credit card you might not be able to mark it paid. Test on a cash test order whether Mark as paid is allowed and what the customer receives. It breaks when orders are marked paid at delivery instead of at payout, or when one order is marked twice.
      7. Returns and refunds. For a fulfilled order whose payment was never collected, Shopify's help page says canceling prevents collecting payment and points you to the returns process. The refund page we read does not mention cash on delivery or other manual payment methods. It breaks when parcels return but the order stays open, or when a refund is paid in cash with no record.
      8. Finance entry. Your accountant needs cash received, cash still with couriers, fees and returns. It breaks when cash still with a courier looks like money in the bank.

      What to automate, in this order

      The early steps need no code.

      1. Tag every cash order. Shopify's page describes Flow as a free app on the Basic, Grow, Advanced and Plus plans, so check that your plan is named there. Its Add order tags action works with triggers such as Order created. Tags are case sensitive, so choose one spelling, such as cod, and keep to it.
      2. Save filtered views. The Orders page filters by payment status, fulfillment status, delivery status, tags and date, and you can save a filter as a view. Make three: cash orders delivered and unpaid, cash orders with failed or attempted delivery, and cash orders unpaid after a set number of days.
      3. Save the waybill on every order. Shopify's fulfillmentCreate mutation accepts tracking information, so the courier's app or connector should write the number there.
      4. Send delivery events into Shopify. Ask your courier or developer how. Our guide to connecting couriers and payment gateways lists the questions.
      5. Alert on exceptions. Flow's Scheduled time trigger runs at most once every 10 minutes and at least once a year, in your store's time zone by default. It provides no order data, so add a get action such as Get order data, and a For each loop to go through the results. Use it to find cash orders delivered and unpaid for too long, tag them and notify a person. For alerts outside Shopify, Flow's reference gives Slack as an example of a connector. The Send HTTP request action (Grow, Advanced and Plus) waits up to 30 seconds for a reply and can retry some failed calls for up to 24 hours when set to Retry.
      6. Match the remittance statement. The Flow pages we read do not show reading a courier file, so this step usually sits in a spreadsheet, a small script or a finance tool. If you use a spreadsheet today, see our guide to moving from spreadsheets to one system.
      7. Mark matched orders as paid. Shopify's help steps are for one order: open it, select Collect payment, then Mark as paid. The orderMarkAsPaid API mutation records a payment for the outstanding balance, needs the write_orders scope and the mark_orders_as_paid permission, and returns a user error if the order cannot be marked as paid, for example when it is already paid. Check the order's state before you treat that error as "already done". Never connect "delivered" straight to "mark as paid". Flow offers a Mark order as paid action from the Fulfillment event created trigger, but the cash is still with the courier then, and Shopify says the action does not capture payment.
      8. Queue returns and refunds. Flow's Refund created trigger starts a workflow when an order is refunded, and its order data lets you add a tag. Shopify notes that returns cannot be created after an order is refunded, so create the return first. Because the refund page we read does not mention manual payments, test a refund on a cash test order and write down who sends the money and how.
      9. Run a regular check. Shopify says webhook messages can repeat and suggests a job that fetches data you may have missed. Review the count of cash orders in each state against what you expect.

      Rules for matching a remittance statement

      • Match on the waybill first and the order number second. Never match on amount alone.
      • Count each statement line once. A repeated line goes to the exception list.
      • Compare amounts in the currency's smallest unit. The ISO 4217 list kept by SIX, published 17 September 2026, shows the Kuwaiti dinar, Bahraini dinar, Omani rial and Iraqi dinar with three minor units, and the UAE dirham, Saudi riyal and Qatari rial with two. A statement rounded to two decimals can show a different total for the same cash, so agree a tolerance, even if it is zero.
      • Record gross cash, fees and net payout as separate amounts.
      • Sort results into four lists: matched, amount differs, on the statement but not in Shopify, and delivered in Shopify but not on the statement.
      • Give every exception an owner and a due date. Do not guess a match.

      Questions to ask your courier about cash

      Remittance terms can differ by courier, and the Aramex FAQ answer we read shows none. Get the answers in writing before you ship the first cash order.

      • How often do you pay out, on which days, and into which account? What changes around public holidays and Eid in each country you serve? Our Ramadan and Eid checklist covers the store side.
      • What does the statement look like? Does each line show the waybill, your reference, amount, currency, delivery date, fee and net amount? Can I download it from a portal or receive it by API?
      • What do you deduct, and where does it show?
      • What happens when a customer pays a different amount from the one on the waybill?
      • How long do you hold a parcel after a failed attempt, and which status tells me it is on its way back?
      • How do I dispute a line, within what time and with what proof?
      • If a parcel is lost after cash is collected, who carries the loss?
      • Can I get a daily list of parcels delivered but not yet paid out?

      A month-end report finance can use

      Agree one layout with your accountant and keep it the same each month. Shopify exports orders as a CSV file. Its page says larger exports and exports by date are emailed, and a separate transactions export covers captured payments only. Check that cash orders you marked paid appear in the transactions file before you build the report on it. The transactions export shows a time offset from UTC, while the page does not say which time zone the order export uses, so agree the cut-off time with your accountant and courier.

      • Cash held by couriers at the start of the month, by courier and currency.
      • Cash orders delivered in the month.
      • Payouts received and matched.
      • Fees and adjustments.
      • Cash held by couriers at month end, grouped by days since delivery. The bands 0 to 7, 8 to 14, 15 to 30 and over 30 are only an example; choose bands that fit your courier's payout schedule.
      • Parcels returned or in transit back, with order value, and the failed delivery count.
      • Open exceptions, with count, value and owner.

      It answers three questions: how much cash is outside your control, which courier is slowest to pay, and which orders need action this week. For the weekly numbers that sit alongside it, see our guide to weekly reporting for a Gulf online store. If the orders also feed your accounts, connecting Shopify to your ERP or accounting system covers who owns which data.

      Your accountant decides how cash held by a courier is recorded. This is general information, not legal or tax advice. Check the current rules or ask a qualified adviser before you decide.

      If you want these steps built into your store and finance routine, ESTASOFT can help with workflow automation. Send a short brief on the contact page.

      Sources

      Written by
      ESTASOFT

      Need help with a project?

      Share a short brief. We reply with next steps.

      Book a call

      30 minutes. Free.

      Tell us about your project and we will suggest a time.

      Or email us at info@estasoft.com