Skip to content

Evidence

Every confirmed order carries an evidence label. It is part of the contract — it is in the API, in the webhook and in the dashboard — because the four ways an order gets confirmed are not equally strong, and you are the one who decides what is strong enough for what value of goods.

evidence What happened What it proves
amount Money landed on an amount exactly one reservation was holding, at a moment that reservation was live for — whether it was still open when we looked, or it had since lapsed and only our own processing was slow to notice. The strongest label. Somebody paid the exact paise figure we handed out, inside the window it was live, and nobody else was holding it.
late The reservation had already lapsed before the payment happened, and exactly one recently-expired reservation at that amount was found. Strong. The amount was not handed to anyone else in between — the rest rule keeps a lapsed amount out of circulation for at least an hour. Weaker than amount only because more time passed.
receipt An Android app reported the UTR the UPI app handed back, and a credit with that reference number arrived. Strong, and independent of the amount — this confirms even if the paise do not match. Android only.
manual You placed a parked credit on an order yourself, by RRN. As strong as your judgement. We record what you decided, along with delta_paise if the amount differed.

A lapsed reservation does not by itself mean late. Both amount and late are reachable once a reservation is no longer open — the difference is not whether we still see it as open, it is whether the payment’s own timestamp falls inside the reservation’s window. If the money moved before the reservation lapsed and only our own processing caught up afterward, that is amount: the customer was not late, we were slow. late is reserved for a payment whose own timestamp shows it arrived after the reservation had already lapsed.

evidence tells you how the match was made. It does not tell you the money is irreversible, and it does not tell you who paid.

  • Confirmation is not a guarantee against a mistake. A false confirmation means you shipped goods for free. That is the failure this whole system is built to make rare and none of these labels can make impossible. If you are shipping something expensive, treat manual with more care than amount.
  • There are no chargebacks here, and no dispute process. There is no mechanism for one, because there is no intermediary holding the money. What reached your account is in your account.
  • Identity is never part of it. payer_vpa and payer_name come back on a confirmed order because they are your receipt. They did not decide anything. The same person shows up under different UPI handles — we have watched one person arrive as two in consecutive tests — people pay from a spouse’s account, and nobody knows which handle belongs to which phone number. So identity is shown and never trusted.

Exactly one rule looks at the payer, and it compares a payer only to themselves: if the same UPI handle paid the same amount within the last 30 minutes, the second credit is parked as duplicate rather than confirming something. That is there because double payments are common and a second identical payment is more often an accident than a second order.

The cost is on Limits: a genuine repeat purchase by the same person at the same price inside half an hour is parked too. The candidate order is listed; it is one click.

Timestamps only ever exclude. A reservation made after the money landed cannot be a candidate for it, so it is dropped. But when two reservations both survive that test, nothing picks the closer one. The credit is parked as ambiguous with both orders listed, and you decide.

This is why a credit that arrives with no usable timestamp at all — a forwarded mail that lost its Date: header — is parked as stale rather than matched against the clock at the moment we received it.

const order = await fetch(`https://moneylanded.com/v1/intents/${id}`, {
headers: { authorization: `Bearer ${process.env.ML_KEY}` },
}).then((r) => r.json());
if (order.status !== 'confirmed') return;
// `late` is present and true only when evidence is 'late'. It is never false.
const wasLate = order.late === true;
switch (order.evidence) {
case 'amount':
case 'receipt':
return ship(order);
case 'late':
return wasLate && ship(order);
case 'manual':
return shipAfterReview(order);
}