Designing an E‑commerce Pricing Engine with Aviator Rule Engine
The article explains how a unified ActivityBO model and three Aviator rule‑chains (check, compute, show) were used to build a flexible pricing‑engine middle‑platform that handles 40+ promotion types, solves allocation precision, supports self‑service configuration, and dramatically reduces deployment time for e‑commerce businesses.
1. Promotion Complexity and Overlap
In mature e‑commerce platforms dozens of promotion types exist, such as multi‑item discounts, full‑reduction, free shipping, single‑item pricing, add‑on upgrades, POS specials, coupons, and gift‑card deductions. The project’s PromotionTypeEnum already defines over 40 enum values and keeps growing. Implementing each promotion with ad‑hoc if‑else logic would be unmaintainable.
Beyond the sheer number of promotion types, the order of applying them (coupon → full‑reduction → gift, etc.) directly influences the final payable amount. Incorrect ordering can cause scenarios where a coupon appears ineffective because a prior full‑reduction reduced the order below the coupon’s threshold.
Another critical issue is how the discount amount is allocated to individual items. For example, a ¥20‑¥3 coupon on a ¥15 coffee and ¥10 tea order must be split so that each item receives at least ¥0.01, otherwise the user perceives a loss. The rounding mode (ROUND_UP vs. ROUND_HALF_UP) determines whether the merchant loses money.
Pitfall: An early version placed coupons after full‑reduction, causing the coupon to miss its threshold. Reordering to apply coupons first resolved the issue.
2. Core Design – Unified Model and Rule Chains
All promotion activities are abstracted into a single ActivityBO object:
public class ActivityBO extends ActivityBaseBO {
// promotion type (101=full‑reduction, 301=free‑shipping, 401=single‑item pricing...)
PromotionTypeEnum promotionType;
// three rule‑chain expressions
String checkExpression; // eligibility check
String computeExpression; // discount calculation
String showExpression; // front‑end label generation
Map<String, Object> metaMap; // parameters used by Aviator functions
Set<GoodsBO> goodsSet; // matched goods
}This unified model enables a single CRUD interface for activity management. Adding a new promotion type only requires a new rule‑chain and corresponding metaMap values; no engine code changes are needed.
The three Aviator expressions form a decoupled pipeline:
checkExpression – validates time window, channel, and order‑level thresholds.
computeExpression – performs the actual discount, free‑item, or price adjustment.
showExpression – generates the label (e.g., "满25减5") and tip shown to the user.
Each expression is a conjunction of function calls, for example:
TimeCycleFunction(activity, price, executeEnum) && ChannelFunction(activity, price, executeEnum) && GoodsMatchAllPriceFunction(activity, price, executeEnum)The engine registers all custom functions (e.g., OffNCentFunction, DiscountNFunction) in a FunctionRegistry during initialization, ensuring they are available to the Aviator evaluator.
Design Insight: The three‑chain separation isolates eligibility, calculation, and presentation concerns, allowing the same ActivityBO to be reused across different promotion types while adhering to the open‑closed principle.
3. Configuration UI and Testing Center
A lightweight middle‑platform UI lets operators create a promotion in four steps: basic info, rule‑chain assembly (drag‑and‑drop functions), meta‑map parameter entry, and scope definition (channel, dining type, store range). The UI validates expression syntax and function existence, so no Aviator knowledge is required.
After configuration, the Calculation Test Center simulates real order scenarios. Operators add mock goods, set order context (channel, delivery fee, dining type), select participating activities, and execute the engine. The test center supports step‑by‑step debugging, showing the intermediate middleGoodsList after each rule‑chain and indicating which function returned false.
Real‑world impact: before the engine, each new promotion required a development cycle of 2–3 days. After deployment, operators can configure and verify a promotion in about 10 minutes.
4. Extensibility Beyond Core E‑commerce
The same architecture applies to other domains:
Food‑delivery / dine‑in – low ticket size, few SKUs, independent delivery‑fee logic.
New‑retail / in‑store – store‑level promotions, membership tiers, breakfast‑card time windows.
Scenario differentiation is achieved through metaMap parameters such as diningType (1=delivery, 2=pickup, 3=dine‑in) and channel (online vs. POS), ensuring the correct rule‑chain path is taken without code changes.
5. Full Closed‑Loop Architecture
The final solution combines five layers:
Unified model ( ActivityBO)
Rule‑chain (Aviator expressions)
Orchestrator ( ComputeService)
Allocation utility ( GoodsPriceShareUtil)
Management UI
This stack delivers a complete closed‑loop from configuration to calculation to monitoring, with measurable improvements in efficiency, correctness, and maintainability.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
Niu Liu
A slightly rustic name 🤠 A tech veteran navigating the internet wave Hardcore tech: fixing all bugs and tough challenges
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
