The Full Cycle in Odoo — Step by Step
1. Purchase Quotation
Purchase › Orders › New QuotationNo accounting effect
The operator enters the vendor, products, quantities, and agreed price. Status: Draft . The agreed price is the reference point for all subsequent operations — receipt, billing, and price variances.
2. Confirmed Purchase Order
Button Confirm Order → status Purchase OrderNo accounting effect
The system generates a pending warehouse receipt. The warehouse operator sees the expected delivery in Ready status.
3. Warehouse Receipt — This is where the accounting event occurs
Inventory › Receipts › Validate⚡ Accounting event fires here
The operator enters the quantities actually received and clicks Validate . Odoo automatically generates a stock.valuation.layer and an account.move :
Dr Stock / Goods Received @ agreed price × qty received
Cr Goods Received Not Invoiced (GRNI) @ agreed price × qty received
Simultaneously: AVCO is recalculated immediately · FIFO layer is created with the receipt date · Stock balance is updated. The invoice has not yet arrived . The liability sits in the GRNI account — not in Accounts Payable.
4. Vendor Bill
GRNI cleared → Accounts Payable
Option A: from the purchase order → Create Bill — Odoo fills in lines automatically via 3-way matching.
Option B: Accounting › Vendors › Bills › New — manual entry without automatic link to the receipt.

Accounting Scenarios at Billing
✓ Scenario 1 — Prices Match
Dr GRNI (Goods Received Not Invoiced) @ agreed price × qty
Cr Accounts Payable @ invoice price × qty
The GRNI account is cleared to zero. The liability is definitively recorded in Accounts Payable.
✓ Scenario 2 — Invoice Price Higher than Agreed
Received @ £10.00, invoiced @ £11.50, quantity 100 units.
Dr GRNI £1,000.00
Dr Purchase Price Variance £150.00
Cr Accounts Payable £1,150.00
The stock value stays @ £10.00. The variance is isolated in the PPV account. The cost of goods already sold is not affected .
✓ Scenario 3 — Invoice Price Lower than Agreed
Received @ £10.00, invoiced @ £9.00, quantity 100 units.
Dr GRNI £1,000.00
Cr Accounts Payable £900.00
Cr Purchase Price Variance (Gain) £100.00
✓ Scenario 4 — Partial Receipt, Full Invoice
Ordered 100 units @ £10.00. Received 60 units. Invoice for 100 units.
At receipt:
Dr Stock £600.00
Cr GRNI £600.00
At billing — 3-way matching warns of a discrepancy. Only 60 units are posted. The remaining 40 units remain as a pending receipt.
Dr GRNI £600.00
Cr Accounts Payable £600.00
✓ Scenario 5 — Invoice Before Goods (Prepaid Invoice)
Common with import shipments. The invoice arrives before the physical goods.
At billing:
Dr GRNI @ invoice price
Cr Accounts Payable @ invoice price
At receipt (after the invoice):
Dr Stock @ invoice price
Cr GRNI @ invoice price
GRNI is cleared. AVCO is updated at the moment of physical receipt — not at the invoice date .
How It Works Without the GRNI Account
In a company with separate systems, the accountant doesn't see the warehouse receipt. They enter the invoice when it arrives:
Dr Stock
Cr Accounts Payable
No GRNI. No price variance account. AVCO is recalculated on the invoice date.
All five scenarios above collapse into one. Partial receipts are invisible. Price variances are absorbed into cost of goods. Prepaid invoices are posted on the invoice date regardless of when the goods actually arrived.

The Numerical Impact on AVCO
Opening balance: 100 units @ £10.00 · Received on 10 Jan: 50 units @ £12.00 · Invoice arrives: 20 Feb · Sold on 15 Jan: 80 units.
✓ Correct Workflow (with GRNI)
10 Jan — AVCO after receipt: (100×10 + 50×12) / 150 = £10.67 15 Jan — COGS at sale: 80 × 10.67 = £853.60 20 Feb — invoice: only clears GRNI ↔ AP COGS unchanged
✗ Without GRNI (invoice is the event)
15 Jan — AVCO at sale: £10.00 (10 Jan receipt invisible) COGS = 80 × 10.00 = £800.00 20 Feb — invoice dated 10 Jan: AVCO retroactively → £10.67 COGS for 15 Jan stays £800.00 January margin overstated by £53.60
Configuration in Odoo
Accounting → Settings → Inventory Valuation
| Setting | Periodic | Perpetual |
|---|---|---|
| When entries are posted | On manual adjustment | At the moment of movement |
| GRNI account | Not used | Used |
| AVCO timing | At invoice date | At receipt date |
| Price variances | Absorbed into cost of goods | Isolated in PPV accounts |
Purchase → Settings → Purchase Order → Control
- 3-way matching — blocks invoices with quantities exceeding received
- Billing policy — based on received quantity, not ordered quantity
With Periodic inventory valuation, all five scenarios above are impossible. The system physically does not generate the journal entry at receipt. The choice of method is a configuration decision. The consequences are structural.
Before You Continue
Five Questions — Answer Without Asking Your Accountant
If you don't know without asking — the answer is: on the invoice date.
If your system is Periodic — no. It's calculated without the latest delivery.
If not — deliveries and invoices are treated as the same event in your accounting system. Physical reality and the documentary record are forcibly merged.
If the answer is "into cost of goods" — every product's margin contains noise from supplier negotiations.
If it gets corrected — decisions made on it are based on a preliminary version of reality.
These questions have no right or wrong answer in themselves. They only have honest and dishonest ones.