Sales Order Sync in Practice: Mapping Wangdiantong Stock-Out Orders to Kingdee Cloud
What This Strategy Solves
In a retail chain, getting online orders from the marketplace into the ERP is one thing; syncing audited and dispatched sales stock-out orders into the financial system as formal delivery documents is another. A retail enterprise we worked with discovered that once its online channels scaled, warehouse movements ran inside one system while financial closing and cost accounting ran inside another. Month-end reconciliation became a manual grind.
We used the Qeasy data integration platform to carry this link: pulling sales stock-out orders incrementally from the source side, applying merge and fault-tolerant processing, then writing them into the target financial system as sales delivery orders. One strategy, two systems, one shared definition—reconciliation now runs on the system, not on people.
Data Flow and Field Mapping
The overall direction is: Source ERP → Qeasy middleware layer → Target financial system. The source is a query-type API (wdt.stockout.order.query.trade) that fetches data incrementally within a time window; the target is an execute-type API (batchSave) that writes documents in batch.
Key field mapping (compiled from the material, desensitized):
| Business Meaning | Source Field | Target Field | Handling Note |
|---|---|---|---|
| Document No. | order_no / stockout_no | FBillNo | Source order number; doc type fixed value WDTXSCKD |
| Stock-out Date | consign_date | FDate | Direct mapping |
| Sales Org | shop_no | FSaleOrgId | Resolved via mapping collection (findCollection) by store code |
| Customer | shop_no | FCustomerID | Store code used as customer identifier |
| Incremental Window | start_time / end_time | — | Dynamically generated as previous day 00:00:00–23:59:59 |
| Status Filter | status | — | Only valid statuses (55 audited, 95 dispatched) |
One key design point: the three dimensions of store/customer/organization share the same source code (shop_no), but each resolves through a different mapping collection. This is the centralized code-mapping pattern commonly used by Qeasy customers—store master data is maintained in one place, and downstream systems pick what they need.
Configuring on Qeasy
Configuration centers on three blocks:
1. Source request assembly
- Incremental start:
start_timeuses_function from_unixtime(({{CURRENT_TIME}}-86400),'%Y-%m-%d 00:00:00'), automatically retrieving yesterday's midnight on each run. end_timeuses yesterday's 23:59:59 the same way.- Set
idChecktotrueso the platform usesstockout_idfor idempotent deduplication, preventing duplicate documents on retries.
2. Middleware merge and fault tolerance
- The material's name contains "merge_fault-tolerant". In practice this maps to: when multiple stock-out records exist under the same original order number (
src_tid), they are merged into one document before writing. Unmappable target values follow a default fault-tolerant policy (skip empties + log errors), without blocking the whole batch. - The header-then-body phased processing is another common Qeasy pattern: commit the header first, then process the body, to avoid leaving half-baked documents.
3. Target batch write
FBillNobinds directly to sourceorder_nofor easy reverse lookup.FSaleOrgIduses_findCollectionagainst an external mapping collection, so a change to a store code takes effect everywhere at once.batchSavesubmits multiple documents in one call; the target side relies on its own document numbering and dedup logic as the safety net.
Implementation Steps
This strategy rolls out in three phases:
Phase 1: Set the incremental starting point. Confirm on the source side that stockout_id is monotonically increasing and indexed by consign_date. Configure the time window function on Qeasy, run a 7-day backfill full reconciliation, and verify that document numbers line up on both sides.
Phase 2: Design the scheduling cadence. Source crontab: 5 0-2/2 * * * (every 2 hours from midnight to 2 AM), off-peak from business hours. Target crontab: 16 4 * * * (one batch write at 4:16 AM). A dense-on-source, sparse-on-target rhythm is the steady play—polling the source too often risks hitting rate limits.
Phase 3: Dual-track operation after launch. Keep incremental and full sync in parallel for the first two weeks: incremental handles daily traffic, full sync runs weekly to check for divergence. Once both sides converge stably, retire full sync and keep only incremental.
Lessons Learned
Pitfall 1: "Midnight drift" in the incremental window. Using CURRENT_TIME - 86400 for yesterday looks safe, but if a midnight job fails and is rerun the next day, it pulls today's data and pushes unclosed documents into the financial system. The steady fix: add a status whitelist (55/95) on the source side and filter out unaudited documents directly.
Pitfall 2: One shop_no, multiple meanings causing mapping collisions. The same store code resolves into mapping collections for sales org, customer, and warehouse. If one row in the mapping table is misconfigured, all three downstream fields are wrong together. A typical mistake is putting "customer mapping" and "org mapping" in the same table. The steady fix: maintain them in separate tables. Qeasy's _findCollection supports namespaces to keep them isolated.
Pitfall 3: "Half-baked documents"—header succeeds, body fails. batchSave submits the whole document. If one line in the body fails validation on the target side, the entire document is rolled back. If Qeasy doesn't propagate the rollback signal to logs, it looks like success. The recommendation: enable "strict target return-code matching" on Qeasy. Anything non-zero counts as failure and triggers a retry, rather than relying only on HTTP 200.
Pitfall 4: Source ID field gets repurposed. The source stockout_id is a numeric primary key and works fine as an idempotency key. But if you later add other commerce channels, src_tid becomes the cross-channel unique identifier. Use src_tid rather than stockout_id as the idempotency key from the start to avoid rework later.
Pitfall 5: Timezone and date format mismatches. Source timestamps carry timezone info; the target expects string dates. Without normalization in the middleware, cross-timezone stores produce the surreal "stock-out date earlier than order date". Adding a normalization step in Qeasy's field mapping is a low-cost, high-return detail.
When to Use and When Not to
Use when: A single-warehouse or multi-store retail enterprise needs to close the loop between the warehouse system and the financial system for online sales stock-outs; daily volume is in the hundreds to thousands, with a stable status machine and clear valid-status set.
Do not use when: Complex distribution scenarios require cross-org, multi-set-of-books document splitting or merging; or when the legacy ERP has no status machine and can only sync via full reconciliation.