Skip to content
Azinove, Home
All insights

Odoo for a trading and distribution company in Saudi Arabia: inventory, imports, multi-currency and bilingual invoicing

What a Saudi trading, wholesale or distribution company needs from Odoo: warehouses and routes, reordering rules, landed costs with customs duty and freight, FIFO or average cost valuation, purchases in dollars, euros or yuan with riyal accounting, B2B price lists and credit control, barcode picking and delivery batches, Arabic and English invoices cleared by ZATCA, and the reports that show margin per customer and ageing stock.

Azinove
Odoo team, Azinove W.L.L (Bahrain)
Odoo screens used to run inventory, purchasing and invoicing for a trading company in Saudi Arabia

A trading company in Saudi Arabia lives on three numbers: what a product really cost once it cleared customs, what margin each customer leaves after discounts and payment terms, and how much stock is sitting in each warehouse and for how long. Most companies we meet in Riyadh, Jeddah and Dammam know the first number only at year end, the second roughly and the third from a spreadsheet. Odoo answers all three, provided the setup is done in the right order: valuation and landed costs before purchasing, purchasing in foreign currencies before sales, and the ZATCA-compliant invoice before the first delivery leaves the dock. This guide walks through that order, with the Odoo documentation behind each statement, and says plainly what Odoo does not do for a Saudi distributor.

Who this is for

Importers and distributors of goods, wholesalers selling to retailers or contractors, and trading houses with a few warehouses across the Kingdom or in Bahrain. Companies that manufacture should read our Bahrain HR guide for the people side and ask us about manufacturing separately; this article is about buying, storing, moving and selling goods.

Company setup: the fields ZATCA checks before anything else

Odoo’s Saudi localization installs the chart of accounts, the 15 % standard VAT, zero-rated and exempt taxes, fiscal positions, withholding taxes and the VAT return. Before it will talk to ZATCA, the company record must carry a company name of at most 63 characters, the full address including district, building number and plot identification, an identification scheme such as the Commercial Registration number, the VAT number, and SAR as the currency. Odoo’s documentation warns that every field must be accurate or onboarding is rejected, and the same applies to customer records. A company with branches enters the parent’s VAT number and each branch’s own Commercial Registration number on the branch contact, and chooses between one central sales journal or one onboarded journal per branch. For a distributor with a Riyadh head office and a Dammam depot invoicing locally, that choice decides how invoice numbering and ZATCA devices are organised, so it is made at the start.

Warehouses, locations and routes

Each physical site is a warehouse in Odoo with a five-character short name that prefixes every document. On each warehouse you choose how goods come in and go out: receive and store in one step, receive then store in two (goods wait in an Input location until put away), or receive, quality control, then store in three. Deliveries work the same way: deliver in one step, pick then deliver, or pick, pack, then deliver. Odoo generates the routes and the Input, Quality Control, Packing Zone and Output locations automatically; the documentation is explicit that these flows should be set on the warehouse, not built by hand with rules. For a distributor the usual pattern is two-step receipts (containers are counted before they are put away) and two-step deliveries (a picker prepares, a checker loads). The Resupply From option lets a regional depot be replenished from the main warehouse with an internal transfer rather than a purchase, and push and pull rules handle the exceptions: a product line that always goes through inspection, returns to a supplier, or a consignment location at a key customer.

Reordering rules and the replenishment report

A reordering rule holds a minimum and a maximum per product and warehouse: when the forecasted quantity drops below the minimum, Odoo proposes a replenishment up to the maximum. The trigger is automatic (a purchase order is created when the scheduler runs or a sales order pushes the forecast below the minimum) or manual, in which case the Replenishment report lists what needs ordering with current and forecasted stock, lead times and arrival dates, and a buyer reviews before clicking Order. The vendor at the top of the product’s vendor price list receives the request for quotation. For imported goods with six to ten weeks of sea freight we set the rules manual, so the buyer consolidates a container rather than letting the system fire ten small orders, and we use the vendor lead time so the forecast looks far enough ahead. Fast-moving local lines can stay automatic.

Valuation: FIFO or average cost, and why it must be decided first

Odoo values stock by one of three costing methods set on the product category: standard cost (a fixed unit cost updated by hand), average cost (the weighted average of all units) or FIFO (first in, first out). Accounting can be periodic, where vendor bills are posted as expenses and stock is adjusted at closing, or perpetual, where bills are posted to stock valuation and cost of goods sold is recorded at each delivery. A distributor that wants to know margin per sale as it happens needs perpetual accounting and either average cost or FIFO. The reason this comes first is the next section: landed costs can only be applied to products in a category valued at average cost or FIFO. Standard cost looks simpler and quietly removes the one feature an importer needs most.

Landed costs: customs duty, freight and insurance into the unit cost

The invoice from a supplier in Guangzhou or Hamburg is not what the goods cost. Freight, insurance, customs duty, port handling and the clearing agent’s fee can add a large share to the purchase price, and a distributor who sells on the supplier price alone is pricing below cost without knowing it. Odoo’s Landed Costs feature, enabled in the Inventory settings with a default journal, adds those charges to the valuation of the received goods. Each type of charge is a service product flagged as a landed cost, with a default split method: equally across products, by quantity, by current cost (expensive items absorb more), by weight or by volume. Freight is normally split by weight or volume, duty by current cost since it is charged on value, and the agent’s flat fee equally.

In practice the forwarder’s bill, the customs duty statement and the insurance invoice arrive as separate vendor bills, often weeks after the container. Odoo lets you add the landed cost line to each bill, click Create Landed Costs, pick the validated receipt it belongs to, compute, review the Valuation Adjustments tab that shows original value, additional cost and new value per product, and validate. The unit cost of every item on that receipt rises, and the margin on the sales that follow is computed on the true cost. Import VAT, which Odoo’s Saudi documentation notes is paid to the Customs Authority at importation at the standard rate, is not a landed cost: it is recoverable input VAT and is booked as such.

Buying in dollars, euros or yuan with riyal books

Odoo’s accounting runs in one main currency, SAR for a Saudi company, and any number of active foreign currencies. Each vendor bill, purchase order and payment carries its own currency; a journal can be fixed to one currency, which is how a USD bank account is modelled; and exchange differences between the bill date and the payment date are posted automatically to a dedicated gain and loss account in an exchange difference journal. Rates can be updated daily, weekly or monthly from a web service chosen in the settings, or entered by hand. The riyal’s fixed peg to the US dollar makes USD purchases predictable, but euro and yuan suppliers move, and a distributor who buys in euros and sells in riyals needs the rate on the bill date, not the rate on the day someone remembered to update it. Odoo also carries the eleven Incoterms and an Incoterm location on each bill and invoice, so the purchasing team records whether a price was FOB Shanghai or CIF Dammam, which decides which landed costs to expect.

Import flow: documents, lots and expiry

The import itself happens outside Odoo, with the customs broker and the Saudi Customs and Fasah platforms; Odoo is where the result lands. A purchase order in the supplier’s currency, a receipt in two steps when the container is unpacked, lot numbers assigned on the receipt for goods that need traceability (Odoo’s Lots & Serial Numbers feature, with expiry dates for food, cosmetics or chemicals), and the landed cost documents attached to the receipt. For products tracked by lot, Odoo refuses to validate a receipt without a lot number, which is the discipline a recall or a near-expiry report depends on. We attach the bill of lading and the customs declaration to the receipt so that the finance team reconciles the duty statement against the goods it covers without leaving the screen.

Selling B2B: price lists, payment terms and credit

A distributor sells the same product at different prices to a hypermarket, a wholesaler and a corner shop, and often in two currencies if it also serves Bahrain. Odoo’s pricelists handle this: each has a currency and optional country groups, and its rules apply to a product or a category as a fixed price, a percentage discount or a formula based on the sales price or the cost, with a minimum quantity and a validity period. The documentation makes a distinction worth knowing: a discount rule shows the discount to the customer on the quotation, a formula rule does not. Payment terms carry due dates and instalments, with an optional early-payment discount, and the follow-up levels send reminders by email, WhatsApp or SMS at the days you set. Odoo also holds a credit limit per customer that warns the salesperson on the quotation; where the business wants a hard stop rather than a warning, we add a validation rule. Credit is where Saudi distributors lose money quietly, so the customer statement and the follow-up report become weekly rituals, not year-end documents.

Picking, delivery batches and the barcode app

The Barcode app processes receipts, deliveries and internal transfers on a phone or a scanner on the warehouse floor, as the operation happens, instead of validating from a desk afterwards. It reads EAN and GS1 barcodes, so a sealed carton’s GTIN, lot and quantity are captured in one scan, and location barcodes confirm where goods were put away or picked from. For deliveries, batch picking groups several orders into one picking list, and the operation type can create batches automatically by customer, carrier, destination country, source or destination location. The dispatch management system goes one step further: vehicles from the Fleet app with a weight and volume capacity, dock locations, and loads built per truck. For a distributor running its own vans across Riyadh, that replaces the morning whiteboard. Delivery methods on the sales order price the shipping as a fixed amount or by rules, and the carrier connectors cover DHL, FedEx, UPS and others for parcels.

Invoicing: Arabic, English and ZATCA

Saudi VAT regulations require tax invoices and simplified tax invoices, and their credit and debit notes, to be in Arabic; they may be bilingual. Odoo handles this in two places: a language on each customer, so documents for that customer are generated in it, and the Gulf Cooperation Council Format option in the Customer Invoices settings, which adds Arabic as the secondary language on tax invoices. The result is one PDF with both languages, which is what a buyer in Jeddah and a parent company in Paris both accept. The Arabic interface is a database language users pick in their preferences, so the warehouse team works right to left while finance works in English if it prefers.

ZATCA’s integration phase, rolled out in waves since January 2023 and still adding waves in 2026, requires the invoicing software to be integrated with ZATCA’s systems. Odoo’s e-invoicing module applies the clearance model to B2B tax invoices and generates the QR code and reports simplified B2C invoices to the Fatoora reporting endpoint. Each sales journal is onboarded separately with a one-time password from the Fatoora portal, in sandbox, simulation and finally production mode; once production is on and an invoice has been submitted, there is no way back. Every submitted invoice stores its UBL 2.1 XML and PDF/A-3 in the chatter permanently, and a rejected invoice stays rejected and is not legally valid until corrected and resubmitted. Credit notes need a ZATCA-approved reason. For the VAT return, zero-rating of exports, reverse charge on foreign services and the withholding tax of 5 % that applies to payments for air and maritime freight, read our guide to Odoo for VAT and e-invoicing in Bahrain and Saudi Arabia; this article does not repeat it.

Hijri dates and the printed documents

Odoo’s accounting and stock move on Gregorian dates, and that is what its invoice and delivery templates print. Odoo’s documentation describes no Hijri calendar display. Where a customer or a board wants the Hijri equivalent on quotations, delivery notes or statements, we add it as a small module that prints the Hijri date next to the Gregorian one on the chosen reports, without touching the dates the accounting uses. The same module usually carries the company’s bilingual letterhead, the Commercial Registration number and the VAT number in the layout ZATCA expects.

Reporting: margin per customer, stock value and ageing

With perpetual accounting, average cost or FIFO and landed costs in place, the numbers a trading company runs on fall out of standard Odoo. The Stock report lists, per warehouse and category, each product’s unit cost, total value, on-hand, free-to-use, incoming and outgoing quantities, with a history and a forecast behind each line. The sales analysis gives margin per product, customer, salesperson and period, because every delivery carries the true cost at the moment it left. The Aged Receivable and Aged Payable reports show who owes what for how long, and the Executive Summary adds gross margin and average debtors days. One report Odoo does not ship is stock ageing: how long each lot has sat in each location. We build it from the stock moves and lots in the project, because for a distributor the capital tied up in slow lines is the number that decides the next purchase.

A typical rollout

Five lots for a Saudi trading company, in the order the data dependencies require
LotScopeGo-live criterion
1. Books and master dataSaudi localization, chart of accounts, SAR and foreign currencies, product categories with costing method, warehouses and routes, customers and vendors with ZATCA fields, opening stock with lotsOpening balance and stock value match the previous system to the halala
2. Purchasing and importsPurchase orders in foreign currencies, two-step receipts, lot numbers, landed cost products and split methods, vendor bills with Create Landed Costs, IncotermsThree real containers received with their duty, freight and insurance in the unit cost
3. Sales and invoicingPricelists per segment and currency, payment terms, credit limits, bilingual invoice layout, ZATCA onboarding in simulation then production per sales journalOne month of invoices cleared or reported by ZATCA with no rejection outstanding
4. Warehouse floor and deliveryBarcode app on receipts and deliveries, batch picking, delivery methods, dispatch with vehicles and docks where the fleet is in-houseA full week of deliveries picked and loaded from the app, stock counts matching
5. Reporting and reorderReordering rules and the replenishment report, stock ageing report, margin and receivables dashboards, follow-up levelsBuyers order from the replenishment report; management reads margin from Odoo, not the spreadsheet

Six mistakes we see

  • Choosing standard cost to keep things simple, then discovering that landed costs cannot be applied and every import margin is overstated.
  • Booking freight and duty as expenses in the profit and loss instead of into stock value, so the margin per sale is wrong and the inventory on the balance sheet is understated.
  • Starting ZATCA onboarding in production mode on a database that still has test invoices, since the switch cannot be undone.
  • Letting automatic reordering rules fire on imported lines with a ten-week lead time, producing a dozen small orders instead of one container.
  • Leaving the customer records without district, building number and identification scheme, so B2B invoices are rejected by ZATCA at clearance.
  • Treating the credit limit as a warning nobody reads: the receivables ageing then becomes the first real report, months too late.

When Odoo is not the right fit

A distributor whose business is dominated by supplier-managed consignment with real-time EDI to a handful of global brands may be better served by that brand’s own portal plus a light accounting system. A company with thousands of daily parcels and a dedicated warehouse management system already tuned for its automation should connect Odoo to it rather than replace it. And a trading company that is not ready to maintain product master data, lots and costing methods will get bad numbers from any ERP; the fix there is a data owner, not software.

Frequently asked questions

Does Odoo have a Saudi localization?

Yes. Odoo 19 ships the Saudi Arabia accounting package with the chart of accounts, 15 % VAT, zero-rated and exempt taxes, fiscal positions, withholding taxes and the VAT return, plus the ZATCA Phase 2 e-invoicing module and its Point of Sale variants.

Can Odoo put customs duty and freight into the cost of the goods?

Yes, with the Landed Costs feature, provided the products belong to a category valued at average cost or FIFO. The charges are added from the vendor bills and split by quantity, value, weight, volume or equally.

Can we buy in US dollars and euros and keep the books in riyals?

Yes. SAR is the main currency, foreign currencies are activated, rates update automatically at the interval you choose, and exchange differences are posted to a dedicated journal. A foreign-currency bank account is a journal fixed to that currency.

Are the invoices in Arabic and English?

Yes. The customer’s language sets the document language, and the Gulf Cooperation Council Format option adds Arabic as the secondary language on tax invoices, which is what the VAT regulations require.

Does Odoo show Hijri dates?

Not as standard: Odoo works and prints in Gregorian dates and its documentation describes no Hijri display. We add the Hijri date to the printed reports where the business wants it.

Does Odoo have a stock ageing report?

Not as a standard report. The Stock report gives value, on-hand and forecast per product; ageing by lot and location is built in the project from the stock moves.

Working with Azinove in Saudi Arabia and Bahrain

Azinove W.L.L is the group’s Gulf company, based in Isa Town, Bahrain (CR 190436-1), and an official Odoo Partner; the group has delivered more than 45 projects. We implement Odoo for trading companies in Riyadh and the Kingdom and in Bahrain, with the tax side described in our VAT and e-invoicing guide and the people side in our Bahrain HR and payroll guide; our guide to choosing an Odoo partner explains how to compare proposals. Send us your number of warehouses, product lines and monthly invoices, and the currencies you buy in, and we come back with a written scope, starting with a 30-minute call.

Sources

  1. Odoo — Documentation 19.0: Saudi Arabia fiscal localization: modules, taxes, import VAT, withholding taxes, company fields required by ZATCA, invoicing language and the Gulf Cooperation Council format, ZATCA Phase 2 clearance and reporting, onboarding modes (read on 23 October 2026) — https://www.odoo.com/documentation/19.0/applications/finance/fiscal_localizations/saudi_arabia.html
  2. ZATCA — E-invoicing: introduction, generation phase and integration phase, tax invoice and simplified tax invoice (read on 23 October 2026) — https://zatca.gov.sa/en/E-Invoicing/Introduction/Pages/What-is-e-invoicing.aspx
  3. ZATCA — Wave 25 of the integration phase, criteria and deadline (24 July 2026) — https://zatca.gov.sa/en/MediaCenter/News/Pages/Wave25-E-invoicing.aspx
  4. Odoo — Documentation 19.0: Landed costs: feature, landed cost products, split methods, AVCO or FIFO requirement, creation from a vendor bill — https://www.odoo.com/documentation/19.0/applications/inventory_and_mrp/inventory/inventory_valuation/landed_costs.html
  5. Odoo — Documentation 19.0: Inventory valuation cheat sheet: standard cost, average cost and FIFO, periodic and perpetual accounting — https://www.odoo.com/documentation/19.0/applications/inventory_and_mrp/inventory/inventory_valuation/cheat_sheet.html
  6. Odoo — Documentation 19.0: Multi-currency system: active currencies, automatic rates and interval, exchange difference journal, currency per journal and account — https://www.odoo.com/documentation/19.0/applications/finance/accounting/get_started/multi_currency.html
  7. Odoo — Documentation 19.0: Incoterms: the eleven Incoterms, Incoterm location, default Incoterm — https://www.odoo.com/documentation/19.0/applications/finance/accounting/customer_invoices/incoterms.html
  8. Odoo — Documentation 19.0: Warehouses and Routes and push/pull rules: one-, two- and three-step receipts and deliveries, resupply between warehouses — https://www.odoo.com/documentation/19.0/applications/inventory_and_mrp/inventory/shipping_receiving/daily_operations/use_routes.html
  9. Odoo — Documentation 19.0: Reordering rules: minimum and maximum, automatic and manual trigger, replenishment report, preferred route — https://www.odoo.com/documentation/19.0/applications/inventory_and_mrp/inventory/warehouses_storage/replenishment/reordering_rules.html
  10. Odoo — Documentation 19.0: Pricelists: currency, country groups, discount, formula and fixed price rules, minimum quantity, validity period — https://www.odoo.com/documentation/19.0/applications/sales/sales/products_prices/prices/pricing.html
  11. Odoo — Documentation 19.0: Payment terms and installment plans, and Follow-up on invoices — https://www.odoo.com/documentation/19.0/applications/finance/accounting/customer_invoices/payment_terms.html
  12. Odoo — Documentation 19.0: Batch picking and Dispatch management system: batch, wave and cluster transfers, automatic batches, vehicles, docks — https://www.odoo.com/documentation/19.0/applications/inventory_and_mrp/inventory/shipping_receiving/setup_configuration/dispatch.html
  13. Odoo — Documentation 19.0: Process receipts and deliveries with barcodes, and Stock report — https://www.odoo.com/documentation/19.0/applications/inventory_and_mrp/barcode/operations/receipts_deliveries.html
  14. Odoo — Source code: Saudi Arabia – E-invoicing module (l10n_sa_edi), LGPL-3 — https://github.com/odoo/odoo/tree/19.0/addons/l10n_sa_edi
Share this analysis
Odoo screens used to run HR and payroll for a company in Bahrain
14 min read

Odoo HR and payroll in Bahrain: GOSI, LMRA work permits and the Wage Protection System

What a Bahrain employer needs from Odoo HR and payroll: employee files with CPR and work-permit expiry, Labour Law hours, overtime and leave, GOSI contributions for Bahraini and expatriate staff, the LMRA Wage Protection System file, work-permit fees and end-of-service rules, and what has to be built because Odoo ships no Bahrain payroll localization.

Read the analysis
GPT-5.6 Sol, Terra, Luna : les nouveaux modeles d'OpenAI
6 min read

GPT-5.6 Sol, Terra, Luna: OpenAI’s New Model Family

OpenAI launches GPT-5.6 in three tiers: Sol (flagship), Terra (balanced), and Luna (fast and affordable). New naming, new pricing, new government oversight: here’s what changes.

Read the analysis
Odoo screens reviewed during the selection of an implementation partner in Bahrain
11 min read

How to choose an Odoo partner in Bahrain and Saudi Arabia: the questions to ask before you sign

The partner decides more of an Odoo project’s outcome than the edition does. How to verify an official Odoo Partner, the ten questions to ask about localization, team, scope, migration, custom code, hosting, training, support, references and exit, and the red flags.

Read the analysis