How to Build Real-Time Inventory Synchronization Between WMS, ERP, and E-Commerce Platforms
Most companies usually start with multiple inventory systems: a warehouse management system to track what’s on the shelf; an ERP to follow what’s been sold, ordered, or invoiced; a Shopify or Magento storefront that shows a number to the customer. That initially works.
The real issue is when none of these three numbers update at the same moment. That gap is what real-time inventory synchronization solves. It aims to keep stock counts consistent across these systems as changes happen, not hours later in a batch job.
In this article, we’re going to cover the core architecture patterns behind this solution, the tradeoffs between request-response and event-driven models, and the failure modes that catch teams off guard the first time they build this. We’ll also discuss API design, performance, security, and monitoring, since none of those are optional once the system is live.
Our scope is deliberately practical. We’re not going to conduct any kind of survey of every ERP or WMS vendor on the market. We’ll walk through the decisions engineering teams face when they connect a warehouse system to an ERP and a storefront and need the numbers to actually match.
Why Inventory Synchronization Is Difficult
There is one main reason that makes inventory synchronization a real challenge: a single SKU can exist in five or six places at once. Each one of the WMS, the ERP, an online store, a marketplace listing, a point-of-sale terminal, and a handheld scanner on the warehouse floor keeps its own count. Moreover, each system has its own idea of “current stock” and updates it on its own schedule.
This usually leads to a set of familiar problems. When a shipment is recorded differently by two systems, duplicate stock counts appear; if a storefront doesn’t know that ten units were already reserved somewhere else, this is where overselling happens. When a nightly batch job hasn’t run yet, stale inventory shows up, allowing a customer to buy something that isn’t actually there. Race conditions happen when two orders try to reserve the last unit within the same second.
Behind those examples is a design problem rather than a bug: most teams design for one inventory number, then discover they have five.
A Typical Architecture
The diagram below illustrates a common architecture for synchronizing inventory between WMS and ERP systems.
This architecture follows the Publish/Subscribe (Pub/Sub) integration pattern. The WMS publishes inventory events, and downstream systems subscribe to the updates they need. Compared to point-to-point integrations, this approach reduces coupling and scales more naturally as additional consumers are introduced. This also settles a common question that’s present in almost every WMS integration kickoff meeting: who owns the number? While ERP systems handle financial processes and planning well, they are not usually the right place for physical stock counts to originate. In most warehouse-first businesses, the WMS should remain the operational source of truth for physical inventory.
A warehouse software integration project usually needs something that serves as a translator between the broker’s internal event format and whatever shape Shopify’s Admin API or Magento’s REST endpoints expect. The most common approach is to have an adapter layer for each of those platforms. Of course, if you have only one storefront, skipping this layer and coupling the WMS directly to it may work, but as soon as another sales channel gets added, the WMS team is suddenly maintaining several separate integrations by hand.
One last thing to be aware of: many enterprise ERPs were built assuming batch imports, not event streams. If your project involves Oracle ERP integration or similar systems, you need to think about having a translation service between the broker and the ERP’s native import format.
The architecture above does not pretend to be exhaustive because vendors and stacks may differ between different projects. However, most real-time inventory synchronization architectures used in WMS ERP integration projects converge on the general pattern shown above.
Synchronization Models: REST, Events, or Batch
There are three main ways to move inventory data between systems. Picking the wrong one for a given case is a common mistake.
| Model | How it works | Best for | Weak point |
| Request-response (REST) | A system calls another system’s API directly and waits for a response | Low-volume lookups, on-demand checks | Doesn’t scale well past a few dozen updates per second; tight coupling between systems |
| Event-driven (Kafka, RabbitMQ, Azure Service Bus, Amazon SQS) | A producer publishes a change, and any number of consumers react independently | High-volume, real-time inventory synchronization across many downstream systems | Requires more operational maturity: dead-letter queues, ordering guarantees, schema management |
| Batch | A scheduled job exports and imports data in bulk | Legacy systems without APIs, end-of-day reconciliation | Not real-time by definition; introduces the “stale inventory” problem directly |
The honest answer is often a mix of those:
- Event-driven messaging to handle the real-time path.
- Batch reconciliation runs on a schedule as a safety net to catch drift in the event stream that could be missed because of downtime or bugs.
- REST calls to perform one-off lookups, for instance, in case a customer service agent wants to check whether an item is in stock right now.
No, exclude the other. All of them contribute to the overall WMS integration work.
How Inventory Events Flow Through the System
A single order touches inventory several times before it’s done. When goods are received into the warehouse, the WMS updates the count. A customer places an order, and the number is reserved instead of being decremented right away. At the time the order ships, the reservation converts into an actual decrement. If the order is cancelled first, the reservation gets released back into available stock instead.
Teams under deadline pressure often skip reservations. Chudovo’s team has been involved in solving an issue from a retailer that ended up overselling within the first week. The root cause behind that: nothing was holding stock between “order placed” and “order shipped.”
Nothing seems to be complex in decrementing stock the moment an order is placed; it breaks the moment an order gets cancelled, edited, or partially fulfilled. By implementing a reservation step, the system has a place to hold that ambiguity without lying to the customer or the warehouse.
Common Failure Modes and How to Avoid Them
A few problems appear in nearly every real-time inventory synchronization project. One of them occurs when two processes try to reserve the same unit at the same time. In this case, a race condition between the two of them could lead to unexpected behaviors such as overselling. A common solution to this is optimistic locking, where a version number gets checked before a write commits. Unlike pessimistic locking, this approach does not require holding a row lock while the transaction is in progress.
Since message brokers generally guarantee at-least-once delivery (but not exactly-once), in case duplicate events exist, consumers might execute the same transaction twice. The key here is idempotency: it implies that processing the same event twice should produce the same result as processing it once. For that purpose, event IDs can be tracked to skip the operation in case some of them have already been processed.
If the service needs to deal with distributed transactions across WMS, ERP, and e-commerce platforms, that’s particularly hard to do correctly with a two-phase commit. What usually works is to apply eventual consistency combined with compensating actions (like releasing a reservation if a downstream step fails).
During a partial outage, unbounded retries can turn a five-minute disruption into a two-hour incident. This is exactly why retry limits and exponential backoff are necessary.
Finally, schema drift causes quieter damage. A field gets renamed in the WMS, a consumer downstream doesn’t get updated, and the failure doesn’t show up as an error. Three weeks later, once someone notices the storefront and the warehouse disagree, this is when the problem really shows up. The way to catch this before it reaches production data is to have versioned event schemas in place, checked at the broker or at the consumer boundary.
API Design for Inventory Synchronization
Whether the integration is REST, GraphQL, or gRPC-based, a few endpoints do most of the work in a typical warehouse management system API:
- GET /inventory: this one reads the current stock for one or more SKUs
- PUT /inventory: in charge of updating the stock directly, used sparingly, mostly for corrections
- POST /inventory/reservations: creates a reservation tied to an order
Chudovo’s engineering team typically starts inventory APIs with a reservation endpoint, since it’s the piece most often designed as an afterthought. Here’s a simplified version of what that looks like:
app.post('/inventory/reservations', async (req, res) => {
const { sku, quantity, orderId, idempotencyKey } = req.body;
const existing = await db.reservations.findByIdempotencyKey(idempotencyKey);
if (existing) {
return res.status(200).json(existing);
}
const result = await db.transaction(async (trx) => {
const stock = await trx.inventory.lockForUpdate(sku);
if (stock.available < quantity) {
throw new InsufficientStockError(sku);
}
await trx.inventory.decrementAvailable(sku, quantity);
return trx.reservations.create({ sku, quantity, orderId, idempotencyKey });
});
res.status(201).json(result);
});
The idempotency key does most of the work here. Without it, a retried request creates a second reservation for the same order, and that’s how phantom stock shortages start. Some other takeaways:
- API versioning matters from the first release, not after the second breaking change.
- Authentication usually means OAuth 2.0 or API keys behind a gateway.
- Pagination keeps large SKU lists workable.
- Consistent error codes let other teams build against the API without asking questions every week.
Performance Considerations at Scale
At enterprise scale, an E-commerce ecosystem has to process thousands of inventory updates per minute. In order to build a resilient architecture that can work under stress, there are a few decisions that matter more than others.
Cached endpoints
Some read-heavy endpoints could increase load on databases, for example, in the case of stock checks made by the storefront. To reduce that, a cache policy should be implemented for those endpoints. Operations that depend on event streaming are a different scenario, because message queues absorb spikes (a warehouse scanner burst doesn’t take down the ERP).
Horizontal scaling
The number of requests a system needs to handle may vary throughout the day. But such a system should be prepared to grow at any time without the need for a full rewrite. To achieve this, teams should implement horizontal scaling of consumers, paired with partitioning by SKU or warehouse.
Database indexing
The inventory database should have appropriate indexes on SKU and location columns. This sounds obvious, but it’s the first thing worth checking when a query that used to take 10ms suddenly takes 400ms.
Back-pressure mechanisms
These are useful to prevent a slow consumer from silently falling behind until it’s hours out of date.
Security Basics You Shouldn’t Skip
Inventory data isn’t sensitive in the way payment data is; still, it could be a target for hackers. OAuth 2.0 is commonly used for authorization, often with JWT access tokens. Authentication and authorization should be enforced through an API gateway rather than implemented independently across individual services. Encryption in transit is table stakes at this point.
Audit logs also matter. Inventory discrepancies get investigated months after the fact, and nobody remembers what happened without a log to check.
If your architecture has an API gateway placed in front of the WMS, ERP, and storefront endpoints, you have a place to enforce rate limits, rotate credentials, and revoke access for a compromised integration key; all of this, without touching every downstream service. In a distributed inventory management setup with several partner integrations, that single choke point is often the difference between a contained incident and a scramble across five codebases.
Monitoring: How You Know It’s Actually Working
A real-time inventory synchronization system that isn’t monitored will fail quietly. Having proper metrics to detect the gap between an event being produced and consumed (event lag) might help to catch most of the issues before a customer does.
Prometheus can collect operational metrics such as event lag and consumer throughput, while Grafana can visualize them. OpenTelemetry can provide distributed traces across WMS, ERP, and storefront calls, allowing teams to follow a single order through the complete workflow.
Dead-letter queues also require active monitoring and review; storing failed messages without investigating them only postpones the problem.
A final note on reconciliation reports. Even with solid event-driven inventory synchronization, running a daily comparison between the WMS count and what the ERP and storefronts show could catch the slow drift that alerts miss. The job is not glamorous, but it’s usually what surfaces a bug before a customer does.
Closing Thoughts
Real-time inventory synchronization is the foundation of reliable eCommerce inventory synchronization across WMS, ERP, and storefronts. As a quick recap, below are some inventory synchronization best practices we’ve discovered in the previous sections:
- One clear source of truth for physical stock
- Event-driven updates as the default path
- Idempotent APIs, especially for reservations
- A defined retry strategy with backoff
- Monitoring of event lag and dead-letter queues
- A message broker that scales horizontally
- API versioning from day one
- An explicit inventory reservation mechanism
Teams that get the reservation model right early spend a lot less time explaining stock discrepancies to angry customers six months in.