codespar_kyc
Identity verification, or open a payments account. Persona, Sift, Konduto and Truora for checks; the licensed BaaS partner for onboarding, which verifies the consumer AND provisions the account that funds codespar_wallet.
Verify counterparties before money moves.
codespar_kyc5 actionsmoves no moneyalways required buyercheck_typecheck_type selects the operation. onboarding and onboarding-business are special: they verify (background check plus documentoscopia) and provision a real payment account for the consumer, so that afterwards codespar_wallet and codespar_pay work for the same consumer_id.
Actions
check_type | What it does | Money | Needs |
|---|---|---|---|
identity | Identity verification of the buyer (Persona) | no | — |
onboardingexample below | Verify a natural person (CPF) AND open a real payment account that becomes their codespar_wallet funding source | no | — |
onboarding-business | Verify a legal person (CNPJ) through its responsible partner AND open the payment account | no | — |
risk-score | Fraud risk score for the buyer (Sift or Konduto) | no | — |
status | Poll a verification by verification_id plus document_number; for onboarding it returns pending, documentscopy_pending, approved or rejected | no | verification_iddocument_number |
Unknown check_type: an unknown `check_type` is refused with `invalid_args`, and so is any `action`: this tool takes none, and the error names `check_type` as the discriminator. `document` and `sanctions` were removed on 2026-09-11 — no provider serves them (ent#1280); for a document-only check use `identity`. Tracked. Measured 2026-09-11.
Names come from the published tool document (/v1/meta-tools.json, the same list the MCP server answers to tools/list); the one-line summaries and the money class are kept in the docs repository and checked against it on every build.
Example
check_type: "onboarding" for a natural person (CPF). In sandbox, a phoneNumber ending in 1 auto-approves both gates.
{
"name": "codespar_kyc",
"arguments": {
"check_type": "onboarding",
"consumer_id": "consumer_0000",
"buyer": {
"fullName": "Example Person",
"document": "00000000000",
"email": "person@example.com",
"phoneNumber": "+5500000000001",
"birthDate": "01-01-2000",
"motherName": "Example Parent",
"address": {
"postalCode": "00000000",
"street": "Example St",
"number": "0",
"city": "Example",
"state": "SP"
},
"country": "BR"
}
}
}const result = await session.execute("codespar_kyc", {
check_type: "onboarding",
consumer_id: "consumer_0000",
buyer: {
fullName: "Example Person",
document: "00000000000",
email: "person@example.com",
phoneNumber: "+5500000000001",
birthDate: "01-01-2000",
motherName: "Example Parent",
address: {
postalCode: "00000000",
street: "Example St",
number: "0",
city: "Example",
state: "SP"
},
country: "BR"
}
});result = session.execute("codespar_kyc", {
"check_type": "onboarding",
"consumer_id": "consumer_0000",
"buyer": {
"fullName": "Example Person",
"document": "00000000000",
"email": "person@example.com",
"phoneNumber": "+5500000000001",
"birthDate": "01-01-2000",
"motherName": "Example Parent",
"address": {
"postalCode": "00000000",
"street": "Example St",
"number": "0",
"city": "Example",
"state": "SP"
},
"country": "BR"
}
})codespar tool codespar_kyc \
-i '{
"check_type": "onboarding",
"consumer_id": "consumer_0000",
"buyer": {
"fullName": "Example Person",
"document": "00000000000",
"email": "person@example.com",
"phoneNumber": "+5500000000001",
"birthDate": "01-01-2000",
"motherName": "Example Parent",
"address": {
"postalCode": "00000000",
"street": "Example St",
"number": "0",
"city": "Example",
"state": "SP"
},
"country": "BR"
}
}'{
"verification_id": "ver_0000"
}Every check_type returns a verification_id. Poll completion with check_type: "status", passing that id and the same document_number; for onboarding the status is pending, documentscopy_pending (with a hosted_url where the consumer finishes document capture), approved (with the funding source) or rejected.
When to use
- Before a consumer can hold funds in live.
onboarding(CPF) oronboarding-business(CNPJ: PJ or MEI) opens the payment account that becomes the wallet's funding source. For a business the documentoscopia target is the responsible partner,buyer.owner[0], not the company. In the test environment the sandbox wallet ships pre-connected and no onboarding is needed. - As a gate before a high-value charge or payout, or when a regulated workflow demands proof of identity:
identity(document plus database check) orrisk-score(behavioural fraud score). - To finish an onboarding: poll
statusuntil it leavespending; while it isdocumentscopy_pending, hand the consumer thehosted_url.
Arguments
| Field | Type | Required | Description |
|---|---|---|---|
check_type | string | Yes | identity | onboarding | onboarding-business | risk-score | status |
buyer | object | Yes | The subject. Verification: { name, document, country, email }. onboarding: { fullName, document (CPF), email, phoneNumber (+55…), birthDate (DD-MM-YYYY), motherName, address, country }. onboarding-business: { document (CNPJ, 14 characters, digits or letters), businessName, tradingName?, businessEmail, contactNumber, businessAddress (or address), owner: [...] }, where owner[] is required and its first entry is the responsible partner (ownerType REPRESENTANTE, full PF data; their CPF is the documentoscopia target) |
verification_id | string | With status | From a prior call. It names the proposal that verified the document, and it is the only thing that provisions a payment account: a status poll without it never binds an account |
document_number | string | With status | CPF (or CNPJ for an onboarding-business proposal). Identifies the subject; it must be the same document the proposal verified and is never used to look an account up |
consumer_id | string | No | Whose account or verification. Defaults to the session user (onboarding and status) |
metadata | object | No | Provider-specific overrides |
Errors and what to do
| Error | Cause | What to do |
|---|---|---|
invalid_args | buyer not an object, check_type missing or unknown. | Fix the call against the Arguments table. |
document_ownership_unproven | A status poll with only a document_number and no verification_id. A document an agent typed is not proof it is the consumer's; nothing is provisioned. | Pass the verification_id the onboarding call returned. |
onboarding_document_mismatch | The document_number on a status poll is not the document the verification_id's proposal verified. | Poll with the same document you onboarded. |
rejected | The provider refused the verification or the onboarding. | Surface it; a rejected onboarding does not open an account. |
Measured 2026-09-11: codespar_kyc takes no action at all. A call carrying one is refused with invalid_args before anything is dispatched, and the error names check_type as the discriminator. The undeclared action: "status" alias this note used to describe was removed in ent#1185, and ent#1182 is closed.
Money and mandate
No money moves on this tool. onboarding and onboarding-business create the payment account the consumer's wallet is funded from; the account is bound only through a verification_id, never through a document number alone, so an agent cannot attach someone's account by typing their CPF. Later spends from that account run under the consumer's signed mandate.
Related
codespar_wallet: the wallet the onboarded account fundscodespar_pay:dda_subscribeneeds the document verified here- SDK reference, verificationStatus
- Async settlement, the KYC sibling and SSE streaming
- Test mode: the sandbox auto-approval rule
Notes
Rails, measured 2026-09-11 against the catalog. identity routes to Persona (default; inquiry_template_id stamped per tenant in connection_metadata) or Truora; risk-score to Sift (INTL) or Konduto (BR fraud); onboarding and onboarding-business to the licensed BaaS partner. status reaches no provider at all: the dispatch answers it directly, reading the onboarding proposal and binding the funding source.
This paragraph previously said document routed to Persona and sanctions to Sift or Truora, carried forward as "previously documented". Neither has a line in the provider catalog, and the catalog is what the router intersects with your connections, so both came back eligibility_empty for every tenant. They are recorded as declared-and-unserved in the API repository (ent#1280) and are no longer offered. For a document-only check use identity, which routes to the same providers.
Operator setup. Persona: API key, and stamp inquiry_template_id in connection_metadata when connecting (per tenant, not passed at execute time; without it inquiry creation fails; the dashboard's Persona connect modal has an input for it). Sift and Konduto: HTTP Basic auth (API key as username, blank password). Truora: API key.
Tracking from the SDK, as previously documented. session.verificationStatus(tool_call_id) and session.verificationStatusStream(tool_call_id, opts) follow the same correlation chain as payments (idempotency_key ↔ external_reference via webhook) and return approved, rejected, review, expired or pending, in that poll-priority order: when several events landed for one tool_call_id, the highest-priority terminal state wins. There is no typed wrapper for the check itself; session.execute("codespar_kyc", arguments) takes the same arguments as the MCP call.
Result shape (SDK), as previously documented. data: { verification_id, status, hosted_url: string | null, check_type }; for onboarding the create call returns hosted_url: null and the document-capture link is surfaced by status. This revision did not re-verify that list against the runtime.
codespar_notify
Send notifications via WhatsApp, email or SMS. Z-API for WhatsApp in Brazil, Twilio for SMS and international WhatsApp, SendGrid for email.
codespar_get_started
Read-only setup planner. Returns the ordered happy path for the authenticated workspace, covering which rails are already connected, what to connect next, and the first calls to try. Moves no money.