Personalised coupon bundles replacing one-size-fits-all segments
Redemption rates improved through relevance scoring and variety constraints
Product substitutability model adopted by eCommerce for fulfilment
Structured test-and-learn framework delivering actionable insights each cycle
Built a product-level offer recommendation engine for a large African grocery retailer, replacing static rule-based coupon assignment with personalised, optimised bundles scored at the customer-product level. The system introduced embedding-based relevance scoring, constraint-based bundle optimisation, and a closed-loop test-and-learn framework, lifting redemption rates and trade spend ROI.
The Problem
A large African grocery retailer ran a loyalty coupon programme reaching millions of customers. Offers were assigned using a handful of business rules: if a customer bought in a category recently, they received the standard coupon for that category. The logic was simple, easy to maintain, and increasingly ineffective.
The Solution
We built an offer recommendation engine that scores relevance at the product-customer level and assembles optimised coupon bundles subject to business constraints. The system replaces rule-based assignment with a two-stage pipeline: candidate generation (which offers could be relevant to this customer?) followed by ranking and bundle optimisation (which combination maximises expected value while satisfying variety, affordability, and budget requirements?).
The foundation was a feature layer capturing how each customer relates to each product. We built product embeddings from transaction data: products appearing in the same baskets, or purchased by the same customers across trips, end up close together in the embedding space. On top of embeddings, we engineered explicit affinity features: purchase frequency, price-point preference, brand loyalty indicators, seasonal patterns, and responsiveness to previous promotions at different discount depths. A ranking model scored each candidate offer against the customer, reflecting predicted likelihood of redemption, incremental spend, and alignment with observed preferences.
The critical differentiator was the bundle optimisation step. Simply taking the top-scoring offers produced repetitive bundles clustered in categories the customer already bought heavily. The optimiser solved a constrained problem for each customer: maximise total expected relevance while enforcing variety constraints (minimum category spread), affordability constraints (discount mix aligned with price sensitivity), fatigue constraints (suppress recently shown offers), and budget constraints (respect per-category and total programme spend limits). This was implemented on Spark, scaling across the full customer base.
Alongside the engine, we designed a test-and-learn framework running structured experiments across campaign cycles: offer type tests, discount depth tests, and messaging tests, each with proper holdout groups. Results fed back into model features and business rules, closing the learning loop that had been missing. A by-product of the embedding work was a product substitutability model that the eCommerce team adopted for fulfilment: when an ordered item was out of stock, the system could suggest a behaviourally plausible substitution rather than defaulting to the nearest SKU by price.
Results and Impact
| Metric | Value |
|---|---|
| Programme engagement | Redemption rates improved as bundles became personalised and varied |
| Trade spend ROI | Budget allocated to offers with measurable incremental impact |
| Offer fatigue | Reduced through individual-level monitoring and cooling-off suppression |
| Learning velocity | Structured test-and-learn framework producing actionable insights each cycle |
| eCommerce fulfilment | Substitutability model adopted by the online team, improving substitution acceptance rates |
| Campaign cycle time | Faster iteration: model-driven bundle generation replaced manual rule configuration |
Key Takeaways
-
Variety constraints mattered as much as relevance scoring. Optimising purely for "most likely to redeem" produced repetitive, category-concentrated bundles that customers quickly ignored. Adding explicit variety and fatigue constraints into the bundle optimisation improved sustained engagement across cycles.
-
Early integration planning prevented the model from living in notebooks. Engaging with the business technology teams from the start to understand SAP integration points and operational constraints meant the model could be deployed into production rather than remaining an analytical exercise requiring manual handoff each cycle.
-
Working across functions unlocked unexpected value. The product substitutability model was built as a by-product of the embedding work. It was the eCommerce team, not the loyalty team, who recognised its value for fulfilment. Analytical assets built in one context often have applications elsewhere, but only if people know they exist.