Acumatica · Customization

Acumatica Receipt Screen — A Deep Dive

Acumatica Receipt Screen — A Deep Dive is the screen the user actually lives in. Every other piece of Acumatica — the workflows, the reports, the integrations — exists to feed.

John Kihiu12 min read

The Purchase Receipts screen (PO302000) is where a PO becomes physical stock. It's built on the graph POReceiptEntry, with POReceipt as the header and POReceiptLine as the detail — but under the hood, confirming a receipt also drives an INRegister/INTran pair, because receiving inventory is, from the Inventory module's point of view, just another stock movement. This dual identity — a PO document that's also an inventory transaction — is the source of most of the screen's customization complexity.

The three-way match

Receipt sits in the middle of the classic three-way match: Purchase Order, Receipt, and AP Bill. A receipt can be entered directly against an open PO (pulling expected quantities and costs from POLine), or, in Drop-Ship scenarios, may not exist at all if the vendor ships straight to the customer. Bills entered from PO301000/AP301000 with "Enter Bill" reference the receipt, not just the PO, which is why cost variances between what was received and what was billed show up as a receipt-vs-bill mismatch rather than a PO-vs-bill one.

Key tabs

Extending POReceiptEntry

A common ask is enforcing that lot/serial numbers follow a specific format or sequence at receipt time, tighter than the generic tracked-item validation Acumatica ships with. Another is blocking receipt against a PO line that's already fully received, beyond the standard over-receipt tolerance setting, for vendors where under- or over-shipping is a known quality issue.

C# · GRAPH EXTENSION
public class POReceiptEntry_Extension : PXGraphExtension<POReceiptEntry>
{
    protected virtual void POReceiptLine_LotSerialNbr_FieldVerifying(PXCache cache,
        PXFieldVerifyingEventArgs e)
    {
        string lot = (string)e.NewValue;
        if (!string.IsNullOrEmpty(lot) && !System.Text.RegularExpressions.Regex.IsMatch(lot, @"^LOT-d{6}$"))
            throw new PXSetPropertyException("Lot number must match the LOT-###### format.");
    }
}

Custom fields and tabs via the Customization Project Editor

Adding a field to POReceiptLine (a QC inspection status, for example) is a standard DAC extension. If that field needs to influence downstream inventory availability — holding received stock until QC passes — that's more than a field: it typically means integrating with the item's Lot/Serial Class hold settings or a custom availability calculation, not just adding a checkbox.

Common validation and event-handler use cases

Beyond lot format and over-receipt checks: defaulting unit cost from the vendor's last actual cost rather than the PO's estimated cost when the PO line was created far in advance, capturing a custom "received condition" field for damaged-goods workflows, and firing a business event when a receipt's cost varies from the PO by more than a tolerance, so purchasing can follow up before the bill is even entered.

Gotchas

Cost on a receipt is frequently provisional — it's the PO's expected cost, not the vendor's actual invoiced cost, and the difference gets trued up when the bill posts (a variance that lands in a landed-cost or purchase price variance account depending on configuration). A customization that treats receipt cost as final will misreport margins for anything received before its bill arrives. Receiving against a closed or cancelled PO line isn't blocked as aggressively as people expect — the receipt-to-PO link is soft enough that a customization enforcing stricter status checks is often a legitimate, common request rather than redundant validation. And confirming a receipt for lot/serial items without assigning numbers at receipt time (rather than at a later count) makes retroactive traceability much harder to reconstruct.

Receipt cost is not bill cost

Any customization reporting on landed cost, margin, or vendor pricing accuracy needs to read from the reconciled cost after the bill posts, not the receipt's cost field alone — otherwise it's reporting on an estimate that both sides expect to change.

Wrapping up

The Receipt screen is a hinge point between purchasing and inventory, and its customizations tend to fail when they treat it as belonging entirely to one side or the other. Respect that receipt cost is provisional, that lot/serial detail captured here is the only reliable trace point, and the screen holds up under the three-way match it was built to support.

John Kihiu
Acumatica ERP Developer · Laravel Engineer

Independent software engineer in Nairobi specialising in Acumatica customisations, Laravel backends, and tax fiscalisation integrations across East and Southern Africa.