Skip to main content
POST
Add a signer to a customer's wallets

Authorizations

x-api-key
string
header
required

Headers

Idempotency-Key
string
required

Caller-generated unique key that lets the server safely replay this request. The cached response is returned for 5 minutes on any retry with the same key from the same API principal. Required on every state-changing money-moving or resource-creating POST.

Required string length: 1 - 128
Pattern: ^[A-Za-z0-9_.:-]{1,128}$

Path Parameters

customerId
string
required

Body

application/json
email
string<email>
required

Email address of the signer to add

Pattern: ^(?!\.)(?!.*\.\.)([A-Za-z0-9_'+\-\.]*)[A-Za-z0-9_+-]@([A-Za-z0-9][A-Za-z0-9\-]*\.)+[A-Za-z]{2,}$
Example:

"signer@example.com"

name
string

Display name of the signer

Example:

"Jane Doe"

role
enum<string>

admin = root-quorum member + signing-quorum member; signer = signing-quorum only

Available options:
admin,
signer
credentialType
enum<string>

How this signer will stamp. api_key requires publicKey.

Available options:
passkey,
api_key
publicKey
string

Machine-signer P-256 compressed public key (33 bytes, 02/03 prefix + 64 hex chars, optional 0x prefix). Required when credentialType=api_key.

Example:

"02a1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6e7f8a9b0c1d2e3f4a5b6c7d8e9f0a1b2"

Response

id
string
required

Unique wallet signer identifier

Pattern: ^wsg_[0-9A-Za-z]{22}$
email
string
required

Signer's email address

Example:

"signer@example.com"

name
string | null
required

Signer's display name

Example:

"Jane Doe"

role
enum<string>
required

admin = root-quorum member + signing-quorum member; signer = signing-quorum only

Available options:
admin,
signer
credentialType
enum<string>
required

How this signer stamps requests

Available options:
passkey,
api_key
passkeyCount
integer
required

Number of passkeys enrolled for this signer

Required range: 0 <= x <= 9007199254740991
Example:

0

status
enum<string>
required

Current signer status

Available options:
pending_activation,
activating,
active,
pending_removal,
removed,
error
createdAt
string<date-time>
required

Timestamp when the signer was created

Example:

"2026-01-15T09:30:00.000Z"

updatedAt
string<date-time>
required

Timestamp when the signer was last updated

Example:

"2026-01-15T09:30:00.000Z"

verificationUrl
string | null
required

Synchronous URL for this add, or null when none applies. Read urlAudience to know who it is for before delivering it — a passkey add returns the signer's enrollment link, an api_key add pending approval returns a customer admin's co-stamp link. On a live roster a "signer" link is the FIRST of two links, not full self-service: after the signer enrolls their passkey the add parks a roster-add ceremony for an admin co-stamp, whose link arrives only on the wallet_ceremony.awaiting_admin_approval webhook (carrying the ceremony's ceremonyId).

Example:

"https://app.conduit.financial/verify/mtQzSU2hdy0DuZ6za2IHIoVDgXzshrFtN38kMULRDFw"

urlAudience
enum<string> | null
required

Audience of verificationUrl: signer = the new signer's credential-enrollment link (deliver to the signer) — on a live roster this is only the first of two links, the second being an admin co-stamp delivered on the wallet_ceremony.awaiting_admin_approval webhook; admin = a customer admin's approval link (deliver to an admin; also delivered via the wallet_ceremony.awaiting_admin_approval webhook); null when there is no URL.

Available options:
signer,
admin
awaitingProvider
enum<boolean>

True only while the parked activity is still resolving at the custody provider — verificationUrl/urlAudience are null here too, but unlike a synchronously-admitted add there is a ceremonyId to track and nothing yet for any human to approve. Absent on every other outcome.

Available options:
true
machineApproval
object

Additional material for a machine (api_key) add that parks for approval on a roster carrying an ACTIVE api_key admin. It is handed back ALONGSIDE verificationUrl (urlAudience: "admin") and the wallet_ceremony.awaiting_admin_approval webhook, which are always present — approve either way. Stamp approvalMaterial with an ACTIVE api_key admin's P-256 key and POST { method: "api_key", credential } to /v2/verifications/{token}/complete (credential is a JSON string of { signedBody, stamp, organizationId }) to activate the signer — the same stamp-and-approve step every machine governance ceremony uses. Absent when the roster has no api_key admin to stamp.