Duplicate Checker API
Pre-filter a phone or email against a company's existing leads before you send it — RevenueScale
Overview
The Duplicate Checker API lets a lead vendor check whether a hashed phone number or email address already exists as a lead for a company before sending that lead. It is a pre-filter gate only — calling this API never creates or modifies a lead. Raw PII never crosses the wire; you send an MD5 hash of the canonicalized value, never the phone number or email itself.
Base URL: https://duplicatecheck.revenuescale.com (also reachable at
https://api.revenuescale.com). Endpoint path is the same on both hosts:
POST /api/v1/duplicate-check
Authentication
Each lead source (vendor) is issued its own API token. The company you send leads to provides you with a token for your feed — reach out to your contact there if you don't have one yet. The token is shown only once when it is created and cannot be retrieved afterward, so store it securely; if it is ever lost or compromised, ask the company to issue a replacement.
Send the token either as a header (preferred) or in the request body:
X-Api-Key: <token>header, or"key": "<token>"field in the JSON body
If both are present, the X-Api-Key header takes precedence.
Canonicalization & hashing rules
Hashes must be computed exactly as described below, or they will never match. This is a public contract — the rules do not change without a coordinated vendor-facing rollout.
| Type | Canonicalization | Then |
|---|---|---|
phone |
Strip everything except digits. If exactly 11 digits and the first digit is
1 (a US country code), drop it. The result must be exactly the
last 10 digits. |
MD5, lowercase hex |
email |
Trim leading/trailing whitespace, lowercase the entire address. | MD5, lowercase hex |
Example: (512) 555-1212 and +1-512-555-1212 both canonicalize to
5125551212 before hashing. Jane@Example.com canonicalizes to
jane@example.com before hashing.
Request
POST /api/v1/duplicate-check — JSON body:
| Field | Type | Required | Notes |
|---|---|---|---|
company |
string | yes | Lowercase company slug. Must match the tenant that owns your API token, or the request is rejected. |
type |
string | yes | "phone" or "email" |
hash |
string | yes | 32-character lowercase hex MD5 digest of the canonicalized value. |
key |
string | only if not sent via header | Your API token. Ignored if the X-Api-Key header is present. |
Response
200 OK with one of:
| Result | Meaning |
|---|---|
| duplicate | The company already has a matching lead on file within the lookback window. Do not send this lead. |
| accepted | No recent match was found — the company does not have this lead, or their record of it is older than the lookback window (see below) and considered stale. Send it the normal way. |
The match spans every lead source the company has, not just yours — a lead ingested through a different vendor is still flagged as a duplicate.
Lookback window
A match only counts as a duplicate when the company's existing lead was created or last updated within the lookback window — 30 days by default. If the most recent matching lead is older than the window, the contact is treated as new and the response is accepted. In other words, a lead the company hasn't worked in more than the window is fair to send again, even though they had it at some point.
Example (default 30 days): a contact the company last touched 12 days ago returns duplicate; the same contact last touched 45 days ago returns accepted.
The window length is configurable and may differ from the 30-day default from one company to the next. If you need a specific company's window, ask your contact there. The duplicate / accepted behavior is the same regardless of the number.
Errors
| Status | Cause |
|---|---|
400 | type is not phone or email, or hash is not a 32-character hex MD5 digest. |
401 | API key missing, unrecognized, or revoked. |
403 | company does not match the tenant that owns the supplied API key. |
Examples
Phone
PHONE="(512) 555-1212"
HASH=$(python3 -c "
import hashlib, re
digits = re.sub(r'\D', '', '$PHONE')
if len(digits) == 11 and digits.startswith('1'):
digits = digits[1:]
print(hashlib.md5(digits.encode()).hexdigest())
")
curl -X POST https://duplicatecheck.revenuescale.com/api/v1/duplicate-check \
-H "Content-Type: application/json" \
-H "X-Api-Key: dc_live_your_token_here" \
-d "{\"company\": \"acme-co\", \"type\": \"phone\", \"hash\": \"$HASH\"}"
EMAIL="Jane@Example.com"
HASH=$(python3 -c "print(__import__('hashlib').md5('$EMAIL'.strip().lower().encode()).hexdigest())")
curl -X POST https://duplicatecheck.revenuescale.com/api/v1/duplicate-check \
-H "Content-Type: application/json" \
-H "X-Api-Key: dc_live_your_token_here" \
-d "{\"company\": \"acme-co\", \"type\": \"email\", \"hash\": \"$HASH\"}"
Both return {"result": "duplicate"} or {"result": "accepted"}.
Security note
MD5 is used here for interoperability with vendor systems that already hash PII this way — not for secrecy. MD5 is cryptographically broken and must not be relied on to keep a phone number or email confidential. Treat your API token as the actual secret: keep it server-side, never embed it in client-side code, and rotate it if you suspect it has leaked.