Part 4: Syncing WooCommerce Customers to Odoo Contacts

Billable hours refers to the time spent on all activities on services for your client or employer that you’re getting payed for.

man wearing black crew-neck shirt

Yann Paul

HR Manager

Management

A calculator ontop a table

Part 4: Syncing WooCommerce Customers to Odoo Contacts

Customer data is one of the most important parts of a WooCommerce to Odoo integration.

Products define what is being sold. Orders define what has been purchased. But customers define who the sale belongs to.

If customer data is mapped incorrectly, the integration can quickly create duplicate contacts, incorrect invoices, disconnected sales history, and messy reporting inside Odoo.

Before syncing WooCommerce customers to Odoo, you need to understand how both systems store customer data and how customer records should be matched, created, and updated.

The main goal is to answer one simple question:

When a customer places an order in WooCommerce, which contact should that order connect to in Odoo?

This article will cover how to sync WooCommerce customers to Odoo contacts, including registered customers, guest customers, billing details, shipping details, company records, duplicate prevention, customer matching, and the res.partner model in Odoo.

Customer Data in WooCommerce

In WooCommerce, customer data is usually created during checkout.

A customer may exist as:

  1. A registered WordPress user

  2. A WooCommerce customer

  3. A guest customer attached only to an order

This is an important difference.

Not every WooCommerce customer has a WordPress user account. Many stores allow guest checkout, which means the customer details are saved against the order, but no permanent user account is created.

For this reason, WooCommerce customer syncing should not only look at WordPress users. It also needs to look at order-level billing and shipping data.

WooCommerce Customer Data

WooCommerce customer data may include:

Customer Data

WooCommerce Source / Field

Customer User ID

wp_users -> ID / wp_postmeta -> _customer_user

Username

wp_users -> user_login

Email Address

wp_users -> user_email / wp_postmeta -> _billing_email

First Name

wp_usermeta -> first_name / wp_postmeta -> _billing_first_name

Last Name

wp_usermeta -> last_name / wp_postmeta -> _billing_last_name

Display Name

wp_users -> display_name

Billing First Name

wp_postmeta -> _billing_first_name

Billing Last Name

wp_postmeta -> _billing_last_name

Billing Company

wp_postmeta -> _billing_company

Billing Email

wp_postmeta -> _billing_email

Billing Phone

wp_postmeta -> _billing_phone

Billing Address Line 1

wp_postmeta -> _billing_address_1

Billing Address Line 2

wp_postmeta -> _billing_address_2

Billing City

wp_postmeta -> _billing_city

Billing State / Region

wp_postmeta -> _billing_state

Billing Postcode / ZIP

wp_postmeta -> _billing_postcode

Billing Country

wp_postmeta -> _billing_country

Shipping First Name

wp_postmeta -> _shipping_first_name

Shipping Last Name

wp_postmeta -> _shipping_last_name

Shipping Company

wp_postmeta -> _shipping_company

Shipping Address Line 1

wp_postmeta -> _shipping_address_1

Shipping Address Line 2

wp_postmeta -> _shipping_address_2

Shipping City

wp_postmeta -> _shipping_city

Shipping State / Region

wp_postmeta -> _shipping_state

Shipping Postcode / ZIP

wp_postmeta -> _shipping_postcode

Shipping Country

wp_postmeta -> _shipping_country

Customer Note

wp_posts -> post_excerpt / order customer note

Order ID

wp_posts -> ID

Order Number

WC_Order -> get_order_number()

Order History

Linked through wp_postmeta -> _customer_user or billing email

For most WooCommerce to Odoo syncs, the most important fields are:

  • Billing email

  • Billing first name

  • Billing last name

  • Billing phone

  • Billing company

  • Billing address

  • Shipping address

  • Customer user ID, if the customer is registered

The billing email is usually the primary field used to match customers between WooCommerce and Odoo.

Customer Data in Odoo

In Odoo, customer data is usually stored in the res.partner model.

This model is used for contacts, companies, customers, vendors, invoice addresses, delivery addresses, and related contact records.

This is different from WooCommerce.

WooCommerce usually treats the customer as a checkout record or WordPress user.

Odoo treats the customer as a contact record that may have multiple related addresses and commercial relationships.

For example, one Odoo customer could be structured like this:

Odoo Record

Purpose

Main Contact

The main customer or company

Invoice Address

The billing address used for invoices

Delivery Address

The shipping address used for deliveries

Contact Person

A person connected to a company

This structure is more powerful, but it also means customer syncing needs to be planned carefully.

Odoo Customer Data

Odoo customer data may include:

Customer Data

Odoo Model / Field

Contact Name

res.partner -> name

Company Name

res.partner -> name where is_company = True

Is Company

res.partner -> is_company

Contact Type

res.partner -> type

Parent Company / Parent Contact

res.partner -> parent_id

Email Address

res.partner -> email

Phone Number

res.partner -> phone

Mobile Number

res.partner -> mobile

Street Address

res.partner -> street

Street Address 2

res.partner -> street2

City

res.partner -> city

State / Region

res.partner -> state_id

Country

res.partner -> country_id

ZIP / Postcode

res.partner -> zip

VAT / Tax ID

res.partner -> vat

Customer Rank

res.partner -> customer_rank

Supplier Rank

res.partner -> supplier_rank

Salesperson

res.partner -> user_id

Pricelist

res.partner -> property_product_pricelist

Payment Terms

res.partner -> property_payment_term_id

Fiscal Position

res.partner -> property_account_position_id

Internal Notes

res.partner -> comment

Company ID

res.partner -> company_id

Language

res.partner -> lang

Active Status

res.partner -> active

Related Sales Orders

sale.order -> partner_id

Related Invoices

account.move -> partner_id

Invoice Address

res.partner -> type = 'invoice'

Delivery Address

res.partner -> type = 'delivery'

Contact Address

res.partner -> type = 'contact'

The most important Odoo model for customer sync is:

res.partner

This is the record that WooCommerce customers will usually map to.

Mapping WooCommerce Customers to Odoo Contacts

Customer mapping is the process of deciding how WooCommerce customer data should connect to Odoo contact data.

At a basic level, the mapping may look like this:

WooCommerce Data

WooCommerce Field

Odoo Data

Odoo Field

Billing First Name + Billing Last Name

_billing_first_name + _billing_last_name

Contact Name

res.partner -> name

Billing Company

_billing_company

Company Name

res.partner -> name / is_company = True

Billing Email

_billing_email

Email Address

res.partner -> email

Billing Phone

_billing_phone

Phone Number

res.partner -> phone

Billing Address Line 1

_billing_address_1

Street Address

res.partner -> street

Billing Address Line 2

_billing_address_2

Street Address 2

res.partner -> street2

Billing City

_billing_city

City

res.partner -> city

Billing State / Region

_billing_state

State / Region

res.partner -> state_id

Billing Country

_billing_country

Country

res.partner -> country_id

Billing Postcode / ZIP

_billing_postcode

ZIP / Postcode

res.partner -> zip

Shipping First Name + Shipping Last Name

_shipping_first_name + _shipping_last_name

Delivery Contact Name

res.partner -> name

Shipping Company

_shipping_company

Delivery Company

res.partner -> name

Shipping Address Line 1

_shipping_address_1

Delivery Street Address

res.partner -> street

Shipping Address Line 2

_shipping_address_2

Delivery Street Address 2

res.partner -> street2

Shipping City

_shipping_city

Delivery City

res.partner -> city

Shipping State / Region

_shipping_state

Delivery State / Region

res.partner -> state_id

Shipping Country

_shipping_country

Delivery Country

res.partner -> country_id

Shipping Postcode / ZIP

_shipping_postcode

Delivery ZIP / Postcode

res.partner -> zip

Customer Note

Order customer note / post_excerpt

Internal Notes

res.partner -> comment

Customer User ID

_customer_user / wp_users -> ID

External Reference

Custom field, for example res.partner -> x_woocommerce_customer_id

Billing VAT / Tax Number

Custom checkout field, for example _billing_vat

VAT / Tax ID

res.partner -> vat

This mapping should be reviewed before customer sync is enabled.

The main question is not just what fields sync.

The main question is how the integration decides whether a customer already exists.

Customer Matching Rules

Customer matching is where most customer sync problems happen.

If the sync does not identify customers correctly, it may create duplicate contacts in Odoo.

For example, the same customer could appear as:

All of these may be the same customer, but Odoo will only know that if the sync has a clear matching rule.

Common matching rules include:

Matching Rule

WooCommerce Field

Odoo Field

Match by Email Address

_billing_email

res.partner -> email

Match by Phone Number

_billing_phone

res.partner -> phone / mobile

Match by Company Name

_billing_company

res.partner -> name where is_company = True

Match by VAT / Tax ID

Custom field, for example _billing_vat

res.partner -> vat

Match by WooCommerce Customer ID

_customer_user / wp_users -> ID

Custom field, for example x_woocommerce_customer_id

Match by WooCommerce Order Billing Details

_billing_email, _billing_phone, _billing_company

res.partner -> email, phone, name

For most WooCommerce stores, email address is the simplest matching field.

The sync process would usually work like this:

  1. A WooCommerce order is placed.

  2. The sync reads the billing email from _billing_email.

  3. Odoo is searched for a res.partner where email matches.

  4. If a matching customer is found, the order is connected to that customer.

  5. If no customer is found, a new res.partner is created.

This works well for simple B2C stores.

However, it may not be enough for B2B stores.

B2C Customer Mapping

For B2C stores, the customer is usually an individual person.

For example:

Field

Value

Name

Sarah Jones

Email

sarah@example.com

Phone

021 123 456

Billing Address

10 Queen Street

Shipping Address

Same as billing

In this case, it is usually fine to create one res.partner record for the customer.

A simple B2C mapping may look like this:

WooCommerce

Odoo

_billing_first_name + _billing_last_name

res.partner -> name

_billing_email

res.partner -> email

_billing_phone

res.partner -> phone

Billing address fields

res.partner address fields

This creates a clean contact record in Odoo.

The WooCommerce order can then be linked to this Odoo customer.

B2B Customer Mapping

B2B customer mapping needs more care.

For B2B stores, the customer may be a company rather than an individual person.

For example:

Field

Value

Company

ABC Dental Limited

Contact Name

Sarah Jones

Email

sarah@abcdental.com

Billing Address

20 Business Park Road

Shipping Address

Warehouse 3, Distribution Road

VAT / Tax ID

123456789

In Odoo, this could be represented as:

Odoo Record

Field Setup

Company

res.partner -> name = ABC Dental Limited, is_company = True

Contact Person

res.partner -> name = Sarah Jones, parent_id = ABC Dental Limited

Invoice Address

res.partner -> type = 'invoice', parent_id = ABC Dental Limited

Delivery Address

res.partner -> type = 'delivery', parent_id = ABC Dental Limited

This is more accurate for B2B, but it requires better mapping rules.

A B2B sync may need to match by:

  • Company name

  • Billing email

  • VAT / Tax ID

  • Existing Odoo company ID

  • Custom WooCommerce customer ID

For B2B stores, email matching alone may not be enough because multiple staff members may order for the same company.

For example:

Customer

Email

Company

Sarah Jones

sarah@abcdental.com

ABC Dental Limited

Mike Brown

mike@abcdental.com

ABC Dental Limited

These should not always become two separate company records in Odoo.

They may need to become two contacts under one company.

Guest Customer Syncing

Guest checkout is common in WooCommerce.

A guest customer places an order without creating a WordPress user account.

In this case, WooCommerce may store the customer data only against the order.

The customer may not exist in:

wp_users

But their billing and shipping details will still exist in order meta fields such as:

_billing_email

_billing_first_name

_billing_last_name

_billing_phone

For guest customers, the sync needs to decide whether to:

  1. Create a new Odoo customer

  2. Match against an existing Odoo customer by email

  3. Create a generic guest customer

  4. Attach all guest orders to one default customer

  5. Only create a customer after payment is completed

For most stores, the best option is to match by billing email first.

If no Odoo customer exists, create a new res.partner.

This gives better customer history, reporting, and invoice records.

However, some stores may prefer not to create a new customer record for every guest checkout, especially if they have a high volume of one-time customers.

This should be decided before the integration is enabled.

Billing and Shipping Addresses

WooCommerce stores billing and shipping information directly against the order.

Odoo can store invoice and delivery addresses as separate contact records.

This creates an important mapping decision.

Should WooCommerce billing and shipping addresses update the main Odoo customer record, or should they create child address records?

A common Odoo structure is:

Address Type

Odoo Setup

Main Customer Contact

res.partner -> type = 'contact'

Invoice / Billing Address

res.partner -> type = 'invoice'

Delivery / Shipping Address

res.partner -> type = 'delivery'

The invoice and delivery address records are usually linked using:

res.partner -> parent_id

For example:

WooCommerce Data

Odoo Record

Customer name and email

Main res.partner contact

Billing address

Child res.partner with type = 'invoice'

Shipping address

Child res.partner with type = 'delivery'

This is useful when the billing and shipping addresses are different.

For example, the invoice may go to the business office, but the delivery may go to a warehouse or branch location.

Updating Existing Customers

Another important decision is whether WooCommerce should update existing Odoo contacts.

For example, if a customer changes their phone number or shipping address in WooCommerce, should that update the Odoo contact?

There is no single correct answer.

It depends on which system is the source-of-truth.

If WooCommerce is the source-of-truth for customer contact details, then updates from WooCommerce should update Odoo.

If Odoo is the source-of-truth, then WooCommerce should not overwrite Odoo customer records without clear rules.

This is especially important for businesses where Odoo is used by sales, finance, account managers, or operations teams.

A customer record in Odoo may contain:

  • Payment terms

  • Salesperson

  • Tax information

  • Pricelist

  • Internal notes

  • Credit control information

  • Accounting settings

These should not be overwritten by basic WooCommerce checkout data.

A safer approach may be:

Field Type

Recommended Update Rule

Name

Create if missing, update carefully

Email

Use for matching, avoid overwriting unless confirmed

Phone

Update if blank or if WooCommerce is source-of-truth

Billing Address

Create/update invoice address

Shipping Address

Create/update delivery address

Payment Terms

Keep controlled in Odoo

Pricelist

Keep controlled in Odoo

Salesperson

Keep controlled in Odoo

VAT / Tax ID

Update only if trusted and validated

The sync should not blindly overwrite every Odoo customer field.

Preventing Duplicate Customers

Duplicate customer records are one of the most common issues in WooCommerce to Odoo integrations.

Duplicates usually happen because:

  • Customers checkout with different emails

  • Existing Odoo contacts have missing emails

  • Company names are written differently

  • Phone numbers use different formats

  • Guest customers are not matched properly

  • The sync creates a new contact before searching properly

  • Billing and shipping contacts are created as main contacts instead of child contacts

Before syncing, it is useful to clean existing Odoo contact data.

Check for:

  • Duplicate emails

  • Missing emails

  • Duplicate company names

  • Inconsistent phone numbers

  • Contacts that should be companies

  • Companies that should be contacts

  • Old inactive customers

  • Missing VAT / Tax IDs

A good customer sync should always search before creating.

The sync logic should usually be:

  1. Search for existing Odoo customer.

  2. If found, use that customer.

  3. If not found, create a new customer.

  4. Store the WooCommerce customer ID or order reference if required.

  5. Link the WooCommerce order to the correct Odoo customer.

This prevents unnecessary duplicate records.

Customer Source-of-Truth

Before syncing customer data, you need to define which system controls which customer fields.

This is the customer source-of-truth.

For example:

Field

Recommended Source-of-Truth

Customer Name

WooCommerce or Odoo

Email

WooCommerce

Phone

WooCommerce

Billing Address

WooCommerce

Shipping Address

WooCommerce

Company Name

WooCommerce or Odoo

VAT / Tax ID

Odoo or validated WooCommerce field

Payment Terms

Odoo

Pricelist

Odoo

Salesperson

Odoo

Internal Notes

Odoo

Customer Account Status

Odoo

A practical setup is:

  • WooCommerce controls checkout contact details

  • WooCommerce controls billing and shipping address data from the order

  • Odoo controls accounting, tax, payment, salesperson, and internal customer fields

This allows WooCommerce to remain the customer-facing storefront, while Odoo remains the operational and accounting system.

Recommended Customer Mapping Rules

A reliable WooCommerce to Odoo customer sync should usually follow these rules:

  1. Use billing email as the primary customer matching field for B2C stores.

  2. Use company name, VAT number, or custom ID for B2B stores where required.

  3. Always search Odoo before creating a new res.partner.

  4. Store the WooCommerce customer ID in Odoo if customers are registered users.

  5. Support guest checkout customers using order billing details.

  6. Do not blindly overwrite existing Odoo customer records.

  7. Store billing and shipping addresses separately if the business needs accurate invoice and delivery records.

  8. Use res.partner -> parent_id to link child contacts to companies or main contacts.

  9. Keep payment terms, pricelists, salesperson, and accounting fields controlled in Odoo.

  10. Clean duplicate Odoo contacts before enabling the sync.

Customer Mapping Checklist

Before syncing WooCommerce customers to Odoo, confirm the following:

  • Are WooCommerce customers mostly B2C, B2B, or both?

  • Does the store allow guest checkout?

  • Should guest customers be created in Odoo?

  • Should every WooCommerce order create a customer record?

  • Should the sync match customers by email?

  • Should the sync match companies by company name?

  • Should the sync match customers by VAT / Tax ID?

  • Should the WooCommerce customer ID be stored in Odoo?

  • Should billing addresses become invoice addresses in Odoo?

  • Should shipping addresses become delivery addresses in Odoo?

  • Should billing and shipping addresses be stored as child contacts?

  • Should WooCommerce update existing Odoo contacts?

  • Which fields should WooCommerce be allowed to update?

  • Which fields should remain controlled by Odoo?

  • What happens if an existing Odoo customer has the same email?

  • What happens if two WooCommerce customers use the same email?

  • What happens if the billing and shipping addresses are different?

  • What happens if the customer changes their address after the first order?

  • How should company customers be handled?

  • How should individual customers be handled?

  • Should inactive Odoo contacts be used or ignored?

  • Should customers be archived, merged, or left unchanged if duplicates already exist?

These questions should be answered before turning customer sync on.

Common Customer Sync Problems

Most customer sync problems come from unclear matching rules or poor data quality.

Problem

Cause

Duplicate customers in Odoo

No clear matching rule

Orders linked to the wrong customer

Email, phone, or company matching not precise enough

Guest orders not syncing correctly

Sync only checks WordPress users and ignores order billing data

Company customers duplicated

B2B company matching not configured

Billing address overwritten

WooCommerce updates the main Odoo contact instead of invoice address

Shipping address missing

Sync does not create delivery address records

Odoo payment terms overwritten

WooCommerce is allowed to update too many fields

Invoices linked to generic customer

Guest checkout mapping not configured properly

Customer reports are inaccurate

Orders are spread across duplicate customer records

VAT details missing

WooCommerce does not collect or map tax ID fields

Most of these problems can be avoided by defining customer matching rules before implementation.

Final Thoughts

Customer syncing is not just about copying names and email addresses from WooCommerce into Odoo.

It is about making sure every WooCommerce order connects to the correct Odoo contact.

For simple B2C stores, this may be as easy as matching customers by billing email and creating a new res.partner when no match exists.

For B2B stores, the process may need to support companies, child contacts, invoice addresses, delivery addresses, VAT numbers, and existing Odoo customer records.

The most important steps are to define the customer source-of-truth, decide how customers are matched, decide how billing and shipping addresses are handled, and prevent duplicate records before they happen.

When this is done correctly, WooCommerce can remain the customer-facing checkout system, while Odoo becomes the reliable source for customer history, sales orders, invoices, accounting, and reporting.

Share on social media

Create a free website with Framer, the website builder loved by startups, designers and agencies.