Case study · Customer data

A customer data platform you can click through

Three brands, 1,603 customer records, no shared ID. This is the working system I built to decide who is the same person, which values to trust, who shares a household, and who can be marketed to. Every number below is real output from the pipeline.

Or explore on your own. Hover or tap for the reasoning.
Mini MDM demo workspace · synthetic data
Loading the workspace…

How I tuned it

The rules started as a spec: points for a shared email, phone, name and zip, a merge line at 70, and a guard for family inboxes. I ran them against the answer key, changed what the results showed was wrong, and ran again. Each row is a full run.

RunWhat changedWrong mergesMissedIn reviewWrong householdsCustomers in audience
1The spec as written016645239
2Phone 30 → 35, typo-aware guard, surname-gated households, hold possible buyers01171301
2*Same rules, harder data: couples on one phone, 21 fathers and sons4111816501
3Email needed to auto-merge, guard covers phones11617301

Run 2 looked finished, and that was the problem. Zero wrong merges meant the test data never tested the rules. Real customer lists have couples who give the same home phone and sons named after their fathers, so I added both. Sixteen sons were fused with their fathers. Raising the merge line couldn't fix it: at 75 the wrong merges go away, but 413 real matches are missed. The review queue also filled with 151 couples. What fixed it was admitting the rules can't tell a son from a father, and handing those pairs to a person, and letting the guard treat a shared phone like a shared inbox.

What that cost. 43 more real matches stay unmerged until someone reviews them, because one person with two emails looks exactly like a father and son. I'd rather a person spend a minute on each than merge a family's consent and addresses.

What I left alone. One wrong merge remains: two newsletter signups, both "Brian" on the Fitzgerald family inbox in the same zip. Every field the rules can see is identical, so the fix is upstream: ask the signup form for a last name. And Amanda Wilson's profile says Willson, because "newest value wins" keeps her newer, misspelled order. The same rule lets one customer into the audience: Grace Baker's newer order says Bauer, so the possible-buyer check misses her. I kept it anyway. A rule that second-guesses the newest value would make every profile harder to explain, and the cost is one email.

The data is synthetic, generated with an answer key the pipeline never sees. The app's numbers come from 2,800 runs of the real pipeline (Python, DuckDB, one test per rule), done ahead of time; the page does no matching of its own.