Structural problem: 4,934 loans (62% of campaign) had never paid on the loan before the campaign. They generated only GHS 366K on GHS 26.4M original debt — 1.4% yield. The 830 loans that paid within 30 days before the campaign generated GHS 2.05M — 5.6× more from 17% of the volume.
Performance by DPD
DPD Band
Loans
Fully Paid
Conversion
Collected
Original Debt
Yield
30–59
2,939
372
12.7%
GHS 2,688K
GHS 17,121K
15.7%
60–89
1,721
66
3.8%
GHS 745K
GHS 9,350K
8.0%
90–119
1,903
33
1.7%
GHS 831K
GHS 10,575K
7.9%
120+
1,367
10
0.7%
GHS 421K
GHS 7,434K
5.7%
DPD 120+: GHS 4.55M discount offered, GHS 421K collected. For every GHS 1 collected, ~GHS 10.8 in discount was ignored.
As expected, the conversion rate for DPD 30–59 was the highest. This aligns with expectations, as this group was exposed to the discount for the first time during this campaign.
Performance by Segment (Prior Payment × DPD)
Payment History
DPD
Loans
Paid
Conversion
Collected
Original Debt
Yield
Paid on campaign day
30–59
82
42
51.2%
GHS 257K
GHS 538K
47.7%
Paid 1–7 days before
30–59
304
89
29.3%
GHS 734K
GHS 1,992K
36.9%
Paid 1–7 days before
60–89
59
14
23.7%
GHS 134K
GHS 345K
38.8%
Paid 1–7 days before
90–119
35
4
11.4%
GHS 56K
GHS 187K
29.8%
Paid 8–30 days before
30–59
526
140
26.6%
GHS 1,061K
GHS 3,225K
32.9%
Paid 8–30 days before
60–89
196
15
7.7%
GHS 255K
GHS 1,162K
22.0%
Paid 8–30 days before
90–119
114
7
6.1%
GHS 195K
GHS 709K
27.5%
Paid 31d+ before
30–59
385
30
7.8%
GHS 390K
GHS 2,424K
16.1%
Paid 31d+ before
60–89
329
19
5.8%
GHS 283K
GHS 1,914K
14.8%
Paid 31d+ before
90–119
537
10
1.9%
GHS 532K
GHS 3,111K
17.1%
Never paid
30–59
1,642
71
4.3%
GHS 247K
GHS 8,941K
2.8%
Never paid
60–89
1,133
16
1.4%
GHS 62K
GHS 5,900K
1.0%
Never paid
90–119
1,212
12
1.0%
GHS 39K
GHS 6,549K
0.6%
Never paid
120+
947
2
0.2%
GHS 18K
GHS 4,992K
0.4%
The conversion rate was highest across all DPD groups for those who had paid within the last 1–7 days.
On the other hand, 62% of the campaign (almost 5,000 loans) had never paid before. They generated GHS 366K — we can assume that without the campaign, these loans would not pay.
Additional Signals
By Balance Size (Due After Discount)
Balance Band (GHS)
Loans
Fully Paid
Conversion
<500
33
11
33.3%
500–1K
344
55
16.0%
1K–2K
2,848
206
7.2%
2K–5K
4,067
202
5.0%
5K+
638
7
1.1%
Achievable amount drives action. Loans under GHS 1K converted at 16–33% — 3–6× the campaign average. Loans over GHS 2K (71% of volume) converted at ≤5%. High balance is the primary friction point: borrowers willing but unable to pay lump sum. Strongest case for tiered instalment offers at 2K+.
By LN Group
LN
Loans
Paid
Rate
4–6
316
9
2.8%
7–10
1,994
74
3.7%
11–15
2,381
126
5.3%
16–20
1,325
85
6.4%
21+
1,914
187
9.8%
By Collection Call Response
Segment
Loans
Paid
Rate
Queue answered
2,333
259
11.1%
IVR only
1,146
89
7.8%
Attempted, no answer
4,450
132
3.0%
All IVR-only loans also had agent attempts — no loans received purely IVR.
SMS Response (INFOBIP_SMS — 6 discount batches)
SMS Batch
SMS Sent
Loans Paid Within 1 Day
Mar 18 — "Second chance"
7,916
100
Mar 20 — "Discount active"
7,814
32
Mar 27 — "Discount reminder"
7,694
37
Apr 1
7,044
36
Apr 6 — Easter SMS
6,311
23
Apr 10 — Last day
6,228
57
Total unique (any batch)
—
285 of 481 (59%)
59% of fully paid loans paid within 1 day of an SMS. First batch (Mar 18) drove the most — borrowers waiting for the offer. Last-day urgency (Apr 10) was second. The first SMS is the highest-leverage send.
What Worked & What Didn't
✓ Worked
DPD 30–59 + paid recently: 27–51% conversion — discount caught active repayers and closed loans
LN 21+: 9.8% overall, 18% at DPD 30-59 — loyal borrowers respond to relationship + offer
First SMS batch: 100 loans paid within 1 day — strongest single channel action
Agent calls: queue-answered loans converted at 11.1% — 3.7× unanswered
Small balances (<GHS 1K due): 16–33% conversion — achievable amount drives action; 3–6× campaign average
✗ Didn't Work
Never paid + DPD 60+: 0.4–1.0% yield — discount wasted on 3,292 loans
LN 4–6 + DPD 60+: near-zero — no relationship equity, no response
4,450 unanswered loans: 56% of campaign never got agent contact — massive unrealised upside
Flat 50% discount for high-intent borrowers: recent payers don't need the full 50% to close — recovering GHS 400–500K more per campaign
Strategy for Next Campaign
Tier 1 — Active repayers
Paid ≤7 days before campaign — all DPD bands
20–35%
Recent payment signal dominates DPD — strong conversion across all bands: DPD 30–59: 29.3% → 20% discount ·
DPD 60–89: 23.7% → 25% discount ·
DPD 90–119: 11.4% → 35% discount
Current rule misses 94 high-intent loans (DPD 60–119) who receive 50% unnecessarily.
Tier 2 — Recent payers
Paid 8–30 days before — DPD 30–59 and DPD 60–89 only
30–40%
Recency signal holds through DPD 60–89 but fades at 90+: DPD 30–59: 26.6% → 30–35% discount ·
DPD 60–89: 7.7% → 40% discount
LN 21+ with last payment 31d+ ago = 8.5% / 7.0% — not enough to pull out of Tier 3.
Stay in campaign with current 50% discount. Covers cold starters (4–8% conversion), deep delinquent (1–2%), and segments where payment recency signal is lost. Low conversion expected — 50% is the floor offer needed to extract any recovery.
Financial impact estimate: Tiers 1+2 cover ~1,120 loans (Tier 1: 398 · Tier 2: 722). Reducing average discount from 50% to ~30% with conservative 15% conversion loss →
+GHS 400–500K incremental recovery per campaign.
Tier 3 unchanged at 50%. No exclusions — everyone stays in campaign.
Decision logic for next campaign
-- Tier 1: paid within 7 days (all DPD)
IF last_pmt ≤ 7d AND dpd 30–59 → 20% discount
IF last_pmt ≤ 7d AND dpd 60–89 → 25% discount
IF last_pmt ≤ 7d AND dpd 90–119 → 35% discount
-- Tier 2: recent payers (DPD ≤89)
IF last_pmt 8–30d AND dpd 30–59 → 30–35% discount
IF last_pmt 8–30d AND dpd 60–89 → 40% discount
Hypothesis: Tier 1 and Tier 2 borrowers convert at the same rate whether they receive a tiered discount (20–40%) or the flat 50%. If true, the tiered discount recovers +GHS 232K more from the A/B group alone, and +GHS 464K if rolled out to all T1+T2 loans in future campaigns.
Test Structure
Tier 1 — Treatment
1,255 loans · paid ≤7d ago
20–35%
DPD 30–59: 20% · DPD 60–89: 25% · DPD 90+: 35% Hypothesis: recent payment means these borrowers don't need 50% to close.
Tier 2 — Treatment
1,289 loans · paid 8–30d ago, DPD <90
30–40%
DPD 30–59: 32.5% · DPD 60–89: 40% Recency signal still warm but weakening — partial discount should hold conversion.
T1 & T2 — Control
2,548 loans · same populations
50%
Flat 50% — same discount as Tier 3. Establishes the baseline conversion rate for active payers receiving the full offer. Direct comparator for treatment groups.
Loan Counts by A/B Group, Tier & DPD
Tier
A/B Group
Discount
DPD 30–59
DPD 60–89
DPD 90–119
DPD 120+
Total
Tier 1
Treatment
20 / 25 / 35%
727
280
127
121
1,255
Tier 1
Control
50% flat
728
280
128
121
1,257
Tier 2
Treatment
32.5 / 40%
710
579
—
—
1,289
Tier 2
Control
50% flat
711
580
—
—
1,291
Tier 3
No test
50% flat
11,478
11,648
13,812
17,592
54,530
Total
14,354
13,367
14,067
17,834
59,622
50/50 random split within each Tier × DPD cell. Source: LOAN_ACCOUNT_HISTORY PERIOD = 2026-05-06, ACTIVE_IN_ARREARS, loan_discount_amount IS NULL.
Expected Repayment Rate — If Strategy Works
Conversion rates from Mar 2026 actuals. Assumption: tiered discount does not reduce conversion vs flat 50%.
Repayment rate = conv% × (1 − discount%) — what % of total debt exposed the campaign recovers.
Group
DPD Band
Loans
Conv Rate
Avg Due (GHS)
Discount
Converters
Repayment Rate
T1 Treatment tiered discount
30–59
727
29.3%
1,901
20%
213
23.4%
60–89
280
23.7%
2,149
25%
66
17.8%
90–119
127
11.4%
2,417
35%
14
7.4%
120+
121
8.0%
2,311
35%
10
5.2%
T1 Treatment subtotal
1,255
avg ~21%
303
18.2%
T1 Control 50% flat
30–59
728
29.3%
1,901
50%
213
14.7%
60–89
280
23.7%
2,149
50%
66
11.9%
90–119
128
11.4%
2,417
50%
15
5.7%
120+
121
8.0%
2,311
50%
10
4.0%
T1 Control subtotal
1,257
50%
304
11.8%
T2 Treatment tiered discount
30–59
710
26.6%
1,734
32.5%
189
18.0%
60–89
579
7.7%
2,055
40%
45
4.6%
T2 Treatment subtotal
1,289
avg ~36%
234
11.4%
T2 Control 50% flat
30–59
711
26.6%
1,734
50%
189
13.3%
60–89
580
7.7%
2,055
50%
45
3.9%
T2 Control subtotal
1,291
50%
234
8.7%
Tier 3 no test · 50%
30–59
11,478
6.0%
1,406
50%
689
3.0%
60–89
11,648
3.5%
1,567
50%
408
1.8%
90–119
13,812
1.5%
1,832
50%
207
0.8%
120+
17,592
0.7%
1,831
50%
123
0.4%
Tier 3 subtotal
54,530
50%
1,427
1.2%
TOTAL CAMPAIGN
59,622
2,502
2.3%
Tier 3 conversion rates: blended from Mar 2026 never-paid + 31d+ segments by DPD. T1/T2 conversion rates from Mar 2026 payment-recency actuals. Tier 1 DPD 120+ rate (8.0%) estimated — no exact data point.
Loans
Half the tier's population — 50/50 random split per Tier × DPD cell. Treatment and control are equal in size by design.
Conv Rate
Observed conversion from Mar 2026 for that exact payment-recency × DPD segment. Same rate applied to treatment and control — the A/B test tells us if treatment diverges.
Avg Due (GHS)
Average TOTAL_DUE per loan at snapshot 2026-05-06 — principal + interest + fees + penalties. Full amount before any discount.
Repayment Rate
conv% × (1 − discount%) — what % of total debt exposed gets recovered. Treatment vs control have same converters; gap comes entirely from the smaller discount. E.g. T1 DPD 30–59: treatment 23.4% vs control 14.7%.
Treatment vs. Control — What We Expect to See
Scenario
T1+T2 Treatment GHS
T1+T2 Control GHS
T1+T2 Gap
Full rollout gain
Verdict
Strategy works Treatment conv ≈ control conv
GHS 745K
GHS 513K
+GHS 232K
+GHS 464K/campaign
Roll out tiered discounts to all T1+T2 in next campaign
Partial win Treatment conv drops ≤15% relative
GHS ~630K
GHS 513K
+GHS 117K
+GHS 234K/campaign
Roll out Tier 1 only; keep Tier 2 at 50% for next test
Strategy fails Treatment conv drops >15% relative
GHS <513K
GHS 513K
negative
no gain
Keep flat 50% — these borrowers need the full offer
T1+T2 Treatment GHS
GHS collected from the treatment half of T1+T2 (2,544 loans). Formula per cell: converters × avg_due × (1 − discount%). Summed across all T1 and T2 DPD bands.
GHS collected from the control half (2,548 loans) — same populations, same conversion rates, but 50% flat discount. Lower GHS per converter because borrower pays only 50% of avg_due.
Example (T1 DPD 30–59): 213 converters × GHS 1,901 × (1 − 50%) = GHS 203K vs treatment GHS 324K
T1+T2 Gap
Treatment GHS minus Control GHS from the A/B group only. This is the incremental GHS earned by giving a smaller discount — assuming conversion held.
GHS 745K − GHS 513K = +GHS 232K from 5,092 test loans
Full Rollout Gain
If the test wins, apply tiered discounts to all T1+T2 loans (not just the test half). Gap doubles because the control group also switches to tiered.
GHS 232K × 2 = +GHS 464K per future campaign
Scenario
Defined by whether treatment conversion rate stays within 15% of control. Works: conv gap ≤15% → tiered discount is free money. Fails: conv gap >15% → borrowers needed the full 50% offer to close.
Comparison — New Strategy vs. Old (Flat 50% for All)
Old strategy — flat 50% all T1+T2
GHS 2,132K
T1 GHS 606K + T2 GHS 420K + T3 GHS 1,106K
New strategy — tiered T1+T2 (if wins)
GHS 2,596K
T1 GHS 938K + T2 GHS 552K + T3 GHS 1,106K
Incremental gain per campaign
+GHS 464K
same converters · lower discount · more GHS per loan
Win condition for A/B test: Treatment conversion rate ≥ 85% of control conversion rate within each Tier × DPD cell.
If this holds, the tiered strategy earns +GHS 232K more from the test group alone — same number of payers, less discount given away.
Primary metric: GHS collected per loan in campaign. Secondary: conversion rate gap between treatment and control.
Database: GHANA_PROD · Campaign cohort filter: loan_discount_start_date::date = '2026-03-17' · Fully paid: loan_discount_amount IS NOT NULL
Methodology notes:
Use loan_discount_start_date (not end_date) for cohort — gives 7,930 loans matching LAH exactly. ·
Prior payment recency must use LAST_REPAYMENT_DATE from LAH at PERIOD = '2026-03-17', not from loan_info_tbl (post-campaign field updated on settlement). ·
Do not join INFOBIP_SMS + MANUAL_CALLS_PRIORITY_DAILY in same query — triggers MCP false write-detection. Use date-based matching instead.
1 — Overall Summary
SELECTCOUNT(DISTINCT loan_id) AS total_loans,
COUNT(DISTINCT CASE WHEN loan_discount_amount IS NOT NULL THEN loan_id END) AS fully_paid_loans,
ROUND(100.0 * COUNT(DISTINCT CASE WHEN loan_discount_amount IS NOT NULL THEN loan_id END)
/ COUNT(DISTINCT loan_id), 1) AS conversion_pct,
ROUND(SUM(total_due_amount), 0) AS due_before_discount,
ROUND(SUM(loan_discount_min_repayment_amount), 0) AS due_after_discount,
ROUND(SUM(total_repayment_amount), 0) AS total_collected,
ROUND(100.0 * SUM(total_repayment_amount) / NULLIF(SUM(total_due_amount), 0), 1) AS yield_pct
FROM GHANA_PROD.ml.loan_info_tbl
WHERE loan_discount_start_date::date = '2026-03-17'
2 — Performance by DPD Band
SELECTCASEWHEN lah.DAYS_LATE < 60 THEN'30-59'WHEN lah.DAYS_LATE < 90 THEN'60-89'WHEN lah.DAYS_LATE < 120 THEN'90-119'ELSE'120+'END AS dpd_band,
COUNT(*) AS total_loans,
COUNT(CASE WHEN lit.loan_discount_amount IS NOT NULL THEN 1 END) AS fully_paid,
ROUND(100.0 * COUNT(CASE WHEN lit.loan_discount_amount IS NOT NULL THEN 1 END) / COUNT(*), 1) AS conversion_pct,
ROUND(SUM(lit.total_repayment_amount), 0) AS total_collected,
ROUND(SUM(lit.total_due_amount), 0) AS original_debt,
ROUND(100.0 * SUM(lit.total_repayment_amount) / NULLIF(SUM(lit.total_due_amount), 0), 1) AS yield_pct
FROM GHANA_PROD.ml.loan_info_tbl lit
LEFT JOIN GHANA_PROD.SEMANTIC_LAYER.LOAN_ACCOUNT_HISTORY lah
ON lit.loan_id = lah.LOAN_ID
AND lah.PERIOD = '2026-03-17'AND lah.LOAN_DISCOUNT_START_DATE = '2026-03-17'WHERE lit.loan_discount_start_date::date = '2026-03-17'GROUP BY 1
ORDER BYMIN(lah.DAYS_LATE)
3 — Performance by Segment (Prior Payment Recency × DPD)
SELECTCASEWHENDATEDIFF('day', lah.LAST_REPAYMENT_DATE::DATE, '2026-03-17'::DATE) IS NULLTHEN'D_never_paid'WHENDATEDIFF('day', lah.LAST_REPAYMENT_DATE::DATE, '2026-03-17'::DATE) <= 0 THEN'A_campaign_day'WHENDATEDIFF('day', lah.LAST_REPAYMENT_DATE::DATE, '2026-03-17'::DATE) <= 7 THEN'B_1-7d_before'WHENDATEDIFF('day', lah.LAST_REPAYMENT_DATE::DATE, '2026-03-17'::DATE) <= 30 THEN'C_8-30d_before'ELSE'E_31d+'END AS pmt_seg,
CASEWHEN lah.DAYS_LATE < 60 THEN'30-59'WHEN lah.DAYS_LATE < 90 THEN'60-89'WHEN lah.DAYS_LATE < 120 THEN'90-119'ELSE'120+'END AS dpd_band,
COUNT(*) AS total_loans,
COUNT(CASE WHEN lit.loan_discount_amount IS NOT NULL THEN 1 END) AS fully_paid,
ROUND(100.0 * COUNT(CASE WHEN lit.loan_discount_amount IS NOT NULL THEN 1 END) / COUNT(*), 1) AS conversion_pct,
ROUND(SUM(lit.total_repayment_amount), 0) AS total_collected,
ROUND(SUM(lit.total_due_amount), 0) AS original_debt,
ROUND(SUM(lit.loan_discount_min_repayment_amount), 0) AS due_after_discount,
ROUND(100.0 * SUM(lit.total_repayment_amount) / NULLIF(SUM(lit.total_due_amount), 0), 1) AS yield_pct
FROM GHANA_PROD.ml.loan_info_tbl lit
LEFT JOIN GHANA_PROD.SEMANTIC_LAYER.LOAN_ACCOUNT_HISTORY lah
ON lit.loan_id = lah.LOAN_ID
AND lah.PERIOD = '2026-03-17'AND lah.LOAN_DISCOUNT_START_DATE = '2026-03-17'WHERE lit.loan_discount_start_date::date = '2026-03-17'GROUP BY 1, 2
ORDER BY 1, 2
4 — Performance by LN Group
SELECTCASEWHEN lit.LN BETWEEN 4 AND 6 THEN'LN_4-6'WHEN lit.LN BETWEEN 7 AND 10 THEN'LN_7-10'WHEN lit.LN BETWEEN 11 AND 15 THEN'LN_11-15'WHEN lit.LN BETWEEN 16 AND 20 THEN'LN_16-20'ELSE'LN_21+'END AS ln_band,
COUNT(*) AS total_loans,
SUM(CASE WHEN lit.loan_discount_amount IS NOT NULL THEN 1 ELSE 0 END) AS fully_paid,
ROUND(100.0 * SUM(CASE WHEN lit.loan_discount_amount IS NOT NULL THEN 1 ELSE 0 END) / COUNT(*), 1) AS conversion_pct,
ROUND(SUM(lit.total_repayment_amount), 0) AS total_collected,
ROUND(SUM(lit.total_due_amount), 0) AS due_before_discount,
ROUND(100.0 * SUM(lit.total_repayment_amount) / NULLIF(SUM(lit.total_due_amount), 0), 1) AS yield_pct
FROM GHANA_PROD.ml.loan_info_tbl lit
WHERE lit.loan_discount_start_date::date = '2026-03-17'GROUP BY 1
ORDER BYMIN(lit.LN)
5 — Performance by Collection Call Response
WITH base AS (
SELECT
lit.loan_id,
CASE WHEN lit.loan_discount_amount IS NOT NULL THEN 1 ELSE 0 END AS fully_paid,
lit.total_repayment_amount AS collected,
lit.total_due_amount AS due_before_discount
FROM GHANA_PROD.ml.loan_info_tbl lit
WHERE lit.loan_discount_start_date::date = '2026-03-17'
),
calls AS (
SELECT
LOAN_ID,
SUM(NUM_QUEUE_ANSWERED) AS queue_ans,
SUM(NUM_IVR_ANSWERED) AS ivr_ans,
SUM(NUM_QUEUE_ATTEMPTS) AS queue_att,
SUM(NUM_IVR_ATTEMPTS) AS ivr_att
FROM GHANA_PROD.SEMANTIC_LAYER.COLLECTION_DAILY
WHERE"Date"BETWEEN'2026-03-17'AND'2026-04-10'GROUP BY LOAN_ID
)
SELECTCASEWHENCOALESCE(c.queue_ans, 0) > 0 THEN'QUEUE_ANSWERED'WHENCOALESCE(c.ivr_ans, 0) > 0 THEN'IVR_ONLY'WHEN (COALESCE(c.queue_att, 0) + COALESCE(c.ivr_att, 0)) > 0 THEN'ATTEMPTED_NO_ANSWER'ELSE'NO_CONTACT'END AS call_segment,
COUNT(*) AS total_loans,
SUM(b.fully_paid) AS fully_paid,
ROUND(100.0 * SUM(b.fully_paid) / COUNT(*), 1) AS conversion_pct,
ROUND(SUM(b.collected), 0) AS total_collected,
ROUND(100.0 * SUM(b.collected) / NULLIF(SUM(b.due_before_discount), 0), 1) AS yield_pct
FROM base b
LEFT JOIN calls c ON b.loan_id = c.LOAN_ID
GROUP BY 1
ORDER BY conversion_pct DESC
6 — SMS Batch Dates
SELECT SENT_AT::date AS sms_date, COUNT(*) AS sms_sent
FROM GHANA_PROD.DATA.INFOBIP_SMS
WHERE SENT_AT::date BETWEEN'2026-03-17'AND'2026-04-10'AND (LOWER(TEXT) LIKE'%discount%'ORLOWER(TEXT) LIKE'%waiver%')
GROUP BY 1
ORDER BY 1
7 — SMS Attribution (Paid Within 1 Day of Any Batch)
WITH sms_dates AS (
SELECT SENT_AT::date AS sms_date
FROM GHANA_PROD.DATA.INFOBIP_SMS
WHERE SENT_AT::date BETWEEN'2026-03-17'AND'2026-04-10'AND (LOWER(TEXT) LIKE'%discount%'ORLOWER(TEXT) LIKE'%waiver%')
GROUP BY 1
),
paid_loans AS (
SELECT loan_id, LAST_REPAYMENT_DATE::date AS repaid_dt
FROM GHANA_PROD.ml.loan_info_tbl
WHERE loan_discount_start_date::date = '2026-03-17'AND loan_discount_amount IS NOT NULLAND LAST_REPAYMENT_DATE IS NOT NULL
)
SELECTCOUNT(DISTINCT p.loan_id) AS paid_within_1d_any_sms,
(SELECTCOUNT(*) FROM paid_loans) AS total_fully_paid
FROM paid_loans p
JOIN sms_dates s ONDATEDIFF('day', s.sms_date, p.repaid_dt) BETWEEN 0 AND 1