Integrating Amazon Seller Central with Odoo sounds simple at first: get the Amazon orders and create matching sale orders in Odoo. The usual approach is to run a scheduled job every few minutes and ask Amazon for new orders.
That works, but I wanted something more immediate.
Instead of continuously polling Amazon, I used the Amazon Selling Partner API Notifications API, Amazon SQS and AWS Lambda. The result is an event-driven integration where Amazon tells us that something has changed, and Odoo reacts to that event.
The basic flow looks like this:
Amazon Seller Central → SP-API ORDER_CHANGE → Amazon SQS → AWS Lambda → Odoo → SP-API Orders API
Receiving Amazon order notifications
The first part of the integration is an SQS Standard queue.
Using the SP-API Notifications API, the application creates a destination pointing to this queue and subscribes to the ORDER_CHANGE notification type.
Amazon then publishes messages whenever there is an important change to an order, such as an order status change or a buyer-requested cancellation. This removes the need to continuously poll the Orders API.
A typical notification contains the Amazon order ID together with information such as:
{ "Payload":{
"OrderChangeNotification":
{ "AmazonOrderId":"123-1234567-1234567",
"OrderChangeType":"OrderStatusChange",
"Summary":{
"OrderStatus": "Unshipped"
}
}
}
}For my integration, SQS is connected to an AWS Lambda function.
Using Lambda as the bridge to Odoo
The Lambda function is intentionally small. It doesn’t try to create the complete Odoo order itself.
Its job is simply to:
Read the SQS message.
Parse the Amazon notification.
Get the AmazonOrderId.
Decide whether the status is relevant.
Send the order ID to Odoo.
Conceptually, the important part is:
notification = payload["OrderChangeNotification"]
if (
notification["OrderChangeType"] == "OrderStatusChange"
and notification["Summary"]["OrderStatus"] == "Unshipped"
):
order_id = notification["AmazonOrderId"]
# Send order_id to Odoo
I prefer this design because AWS only handles the notification transport. The actual business logic stays inside Odoo, where products, taxes, warehouses, invoices and stock already live.
It is also worth separating the Amazon statuses. An Unshipped notification can create the sale order, while a later Shipped notification can update the existing order and validate the related delivery.
Creating the order inside Odoo
The custom Odoo module exposes an endpoint that receives the Amazon order ID.
For example:
POST /web/binary/create_amzn_sale_order
with:
{
"order_id": "123-1234567-1234567"
}
Odoo then takes over.
The endpoint first checks whether an order with the same Amazon order ID already exists. If it does, it avoids creating another one.
If the order is new, Odoo obtains an LWA access token using the Amazon refresh token and calls the SP-API Orders API to retrieve the complete order information.
From there the endpoint handles the normal Odoo business logic.
It determines whether the order is FBA or FBM and selects the corresponding warehouse. It finds the correct currency and pricelist, creates the sale order, matches Amazon products with Odoo products, calculates the applicable marketplace tax and creates the sale order lines.
The endpoint also stores Amazon-specific information directly on the Odoo sale order, including the Amazon order ID, marketplace, country, sales channel, fulfillment channel and Amazon order status.
One useful part of the implementation is the fallback handling. If an Amazon ASIN cannot be matched with an Odoo product, a configurable Product Not Found product is used and the order is flagged for review instead of simply failing.
Handling duplicates is important
An event-driven integration also needs to assume that the same event can arrive more than once.
Amazon uses SQS Standard queues for this workflow, and Standard queues can occasionally deliver duplicate notifications or deliver events out of order. Amazon therefore recommends designing the consumer to tolerate duplicate messages.
Checking AmazonOrderId before creating an Odoo order is a good first layer. In production I would go further and store Amazon’s NotificationId as well as enforce a unique database constraint on the Amazon order ID.
I would also configure an SQS dead-letter queue so that a problematic order can be investigated without blocking the normal flow.
Final result
What is good about this architecture is that each component has a very small responsibility.
Amazon detects the change. SQS provides a reliable buffer. Lambda converts the notification into a simple request. Odoo performs the actual ERP work.
There is no cron job checking Amazon every few minutes and no unnecessary polling when nothing has happened.
For me, that is the main advantage of using the SP-API Notifications API: Amazon becomes the trigger, while Odoo remains the system where the business process is controlled.
It turns a traditional Amazon-to-ERP synchronization job into a much cleaner, near-real-time integration.