TrustCheck with full AI analysis
Runs the complete analysis pipeline on top of a standard TrustCheck: the trust narrative and overview from ?ai=true, plus fraud-pattern detection and AI name matching. Same request body as POST /v1/validate, with three optional flags to switch individual analyses off.
What this endpoint adds
ai_insights.trust_enhancementandai_insights.overview: exactly as on/v1/validate?ai=true.ai_insights.fraud_detection: a risk level, confidence, and patterns for this subject, alongside an aggregate view of your own recent request stream used as velocity context.ai_insights.name_matching: how the submittednamecompares to the matched record, accounting for nicknames, transliteration, middle names, and typos.
Authentication
Identical to the base endpoint: X-API-Key: tm_... or Authorization: Bearer tm_.... An enhanced call counts as one regular check; there is no AI surcharge on current plans.
Request body
A TrustCheck describes one person. Send their name, then whichever contact points you have as flat arrays. Each array holds up to five values.
name is the only field the API requires, but a name on its own is a much weaker check than it looks. With one field there is nothing to cross-reference, so the response can only tell you whether that name appears in the identity graph — not whether it belongs to the person your user is dealing with. Send at least one of emails, phones or addresses alongside it and the result becomes a statement about an identity rather than about a string.Request Body
Example 1: one value per field
One name, one email, one phone, one address. This is the shape most integrations start with.
POST https://api.trustmatch.app/v1/validate/enhanced
X-API-Key: tm_YOUR_KEY
Content-Type: application/json
{
"name": "Jane Q Doe",
"emails": ["jane@example.com"],
"phones": ["6615550101"],
"addresses": [
{
"street": "123 Main St",
"city": "Austin",
"state": "TX",
"zip": "78701"
}
],
"intent": "online-dating",
"include_trust_enhancement": true,
"include_fraud_detection": true,
"include_name_matching": true
}Example 2: one person, up to 5 of each
Same person, three emails, three phones, three addresses. Note the partial addresses: the second has no zip, and the third is a street on its own. Both are valid, and both are checked.
POST https://api.trustmatch.app/v1/validate/enhanced
X-API-Key: tm_YOUR_KEY
Content-Type: application/json
{
"name": "Jane Q Doe",
"emails": [
"jane@example.com",
"j.doe@work.example.com",
"jqd1982@example.net"
],
"phones": [
"6615550101",
"6615550102",
"2145550147"
],
"addresses": [
{
"street": "123 Main St",
"city": "Austin",
"state": "TX",
"zip": "78701"
},
{
"street": "9 Oak Ave",
"city": "Dallas",
"state": "TX"
},
{
"street": "44 Pine Rd"
}
]
}input and match_status are a verdict collapsed across every value you sent. The per-value truth is input_validation.<field>.inputs[], one row per submitted value, in submission order. Key rows by input, not position: phones are stripped to digits before matching.Legacy shape
An earlier version of this API took the upstream graph's own shape, with nameAddresses, emailAddresses, and phoneNumbers. It still works and is not deprecated, so existing integrations need no change. New ones should use the shape above. Sending both forms of the same field is rejected rather than silently resolved.
{
"operation": "validate",
"nameAddresses": [
{
"fullName": "Jane Q Doe",
"address": {
"line1": "123 Main St",
"city": "Austin",
"region": "TX",
"postalCode": "78701",
"countryCode": "US"
}
}
],
"emailAddresses": ["jane@example.com"],
"phoneNumbers": ["6615550101"]
}Response
200 for Example 1, trimmed to what this endpoint adds. Everything outside ai_insights is identical to the base endpoint, including input_validation.<field>.inputs[] for multi-input requests.
Response Model
{
"success": true,
"request_id": "5f3c8b1e-2a4d-4e9c-b6a1-9c7e3f1d8b25",
"trustworthiness_score": 87,
"status": "HIGH",
/* …input_validation, scores, history: identical to POST /v1/validate… */
"ai_insights": {
"ai_enabled": true,
"trust_enhancement": {
"ai_enabled": true,
"feature": "trust_enhancement",
"model": "gemini-3.6-flash",
"intent": "online-dating",
"ai_trust_analysis": {
"summary": "Strong, consistent identity match with a multi-year history.",
"key_factors": [
"Name, email, phone and address all resolve to the same primary identity.",
"Identity first seen over four years ago with recent activity."
],
"red_flags": [],
"recommendations": [
"Video chat before meeting in person.",
"Do not send money, even with a strong verification."
]
}
},
"fraud_detection": {
"ai_enabled": true,
"feature": "fraud_detection",
"model": "gemini-3.6-flash",
"fraud_analysis": {
"risk_level": "LOW",
"confidence": 0.86,
"patterns_detected": [],
"velocity_concerns": false,
"consistency_issues": [],
"stream_observations": [
"Caller submitted 4 checks in the recent window; no unusual cadence."
],
"recommendation": "No fraud patterns detected for this subject. Proceed with standard precautions."
},
"history_analyzed": 4,
"request_stream": {
"records_in_window": 4,
"catfish_flag_count": 0,
"earliest_timestamp": "2026-09-08T14:02:11Z",
"latest_timestamp": "2026-09-11T09:41:37Z"
},
"scope_note": "fraud_analysis describes the submitted subject. request_stream describes this API caller's own recent traffic and is not a statement about the subject."
},
"name_matching": {
"ai_enabled": true,
"feature": "name_matching",
"model": "gemini-3.6-flash",
"provided_name": "Jane Doe",
"matched_name": "JANE A DOE",
"name_analysis": {
"match_confidence": 96,
"variation_type": "partial",
"same_person_likely": true,
"concerns": [],
"explanation": "Matched record carries a middle initial the caller omitted; otherwise identical."
}
},
"overview": {
"overview": "Jane Doe's identity verifies cleanly across every channel you submitted, with no catfish signals.",
"key_findings": [
"All four contact channels resolve to one dominant identity.",
"Identity history spans 4+ years, well above the catfish threshold."
],
"positive_signals": [
"Email and phone both match the primary identity."
],
"risk_factors": [],
"recommended_actions": [
"Video chat before any in-person meeting.",
"Never send money to someone you have not met."
],
"review_priority": "AUTO_APPROVE"
}
}
}Field reference
ai_insights.ai_enabled:truewhen the AI pipeline ran. Each feature block also carries its ownai_enabled; a block withai_enabled: trueand anerrorkey means that one analysis failed while the rest succeeded. The base response is always complete.fraud_detection.fraud_analysis.risk_level: one ofLOW,MEDIUM,HIGH, withconfidence0–1.patterns_detected[],consistency_issues[], andrecommendationdescribe the submitted subject only.fraud_detection.request_streamandstream_observations[]describe your recent API traffic (counts and a time span, never other subjects' outcomes).velocity_concernsis derived from it. Readscope_notebefore rendering any of this next to a subject's name.name_matching.name_analysis.match_confidence: 0–100.variation_typeis one ofexact,nickname,cultural,transliteration,typo,partial,no_match.same_person_likelyis the boolean summary.name_matching.matched_name: the name on the record the graph resolved to, ornullwhen nothing matched. When no name was matched at all, the block reportsskipped: true.overview.review_priority: one ofAUTO_APPROVE,MANUAL_REVIEW,AUTO_REJECT. Treat as a hint, not a decision.
fraud_detection reasons over the scores and match flags of this request and the cadence of your own API calls. It has no access to criminal, credit, employment, or tenancy data, and its output must not be used for any decision covered by the Fair Credit Reporting Act. TrustMatch is built for dating safety, private sales, sending money, and real-life meetups.Intent: tailoring the AI narrative
The optional intent field tells TrustMatch what situation the check is for. The Gemini overview adjusts its positive_signals, risk_factors, and recommended_actions to match: the same scores get a different story. The numeric trustworthiness_score and signal status flags are intent-agnostic.
POST /v1/validate call it is recorded but has no visible effect; the base response shape is unchanged.