POST
/
v1
/
access-management
/
invite
/
customer
curl --request POST \
  --url https://api.next.orenda.finance/v1/access-management/invite/customer \
  --header 'Authorization: Bearer <token>' \
  --header 'Content-Type: application/json' \
  --header 'x-program-id: <api-key>' \
  --data '
{
  "email": "ada.lovelace@example.com",
  "firstName": "Ada",
  "lastName": "Lovelace",
  "dob": "1985-12-10",
  "nationality": "GB",
  "phone": "+447700900123",
  "address": {
    "addressLine1": "12 Analytical Way",
    "addressLine2": "Floor 2",
    "city": "London",
    "state": "Greater London",
    "country": "GBR",
    "postalCode": "EC1A 1BB"
  },
  "isPrepaidCardCustomer": true,
  "accountId": "8f1a2b3c-4d5e-4f6a-8b7c-9d0e1f2a3b4c",
  "confirmation": {
    "method": "passkey",
    "passkeySession": "AYABeJ...custom-auth-session",
    "assertion": "{\"id\":\"q1n...\",\"response\":{\"signature\":\"MEUCI...\"}}"
  }
}
'
{
  "success": true,
  "data": {
    "message": "Customer invitation processed successfully"
  }
}
{
"success": false,
"code": "<string>",
"message": "<string>"
}
{
"success": false,
"code": "<string>",
"message": "<string>"
}
{
"success": false,
"code": "<string>",
"message": "<string>"
}
{
"success": false,
"code": "<string>",
"message": "<string>"
}
{
"success": false,
"code": "<string>",
"message": "<string>"
}
Creates an invited customer from the back-office. Send Authorization: Bearer <access_token> and x-program-id on the request, plus a step-up confirmation. A back-office invite comes in two shapes:
  • Plain customer — just email (and the step-up). The invitee onboards as a standalone customer.
  • Sub-role member — set one of the sub-role flags below. The invitee onboards as a pseudo account funded from a real parent account, so a funding accountId is required.
Consumers inviting their own sub-users call the same route on the customer API, with a different request shape (sub-role only). This page documents the back-office request.

Sub-role flags

Setting any of these makes the invitee a funded sub-role member and requires accountId:
FlagMember type
isPrepaidCardCustomerPrepaid-card customer drawing on the parent’s prepaid master account
isCardOnlyCard-only member (no standalone account)
isSpouseSpouse member
isChildChild member
Omit all four to invite a plain customer.
{
  "email": "grace.hopper@example.com",
  "confirmation": {
    "method": "totp",
    "totp": "123456",
    "accessToken": "eyJraWQiOi…inviter-access-token"
  }
}

Member details

Beyond email (always required) and accountId (required for a member), which member details you must supply depends on the member type:
  • some members need only email + accountId (they complete their own details, or inherit them from the funding account);
  • some need the member’s identity — firstName, lastName, dob, nationality;
  • some need a full profile, including address and phone.
You don’t have to track which is which: send what you have, and if a field is required for that member the API responds 400 naming it. Treat that response as authoritative.
address and phone may be taken from the funding account holder for some member types — in that case you don’t send them. If they’re required and not inherited, the 400 will say so.
{
  "email": "katherine.johnson@example.com",
  "isChild": true,
  "accountId": "8f1a2b3c-4d5e-4f6a-8b7c-9d0e1f2a3b4c",
  "firstName": "Katherine",
  "lastName": "Johnson",
  "dob": "2012-08-26",
  "nationality": "GB",
  "address": {
    "addressLine1": "10 Mercury Way",
    "city": "Hampton",
    "state": "VA",
    "country": "US",
    "postalCode": "23666"
  },
  "confirmation": {
    "method": "totp",
    "totp": "123456",
    "accessToken": "eyJraWQiOi…inviter-access-token"
  }
}

Funding account (sub-role invites)

When any sub-role flag is set, accountId (a UUID) is required and names the parent account the invitee draws against. It’s validated before any user is created — it must:
  • exist,
  • be ACTIVE,
  • not itself be a pseudo account, and
  • be reachable by the caller — in the operator’s program; for a custodian operator, under the inviting custodian.
Failures are non-revealing: an account that doesn’t exist, isn’t in scope, or isn’t reachable all collapse to 400 account not found or not eligible, so the endpoint never discloses cross-tenant account existence. A program-wide operator additionally sees the distinct account is not active / account cannot be a pseudo account messages.

Pay-in IBAN

payInIBAN is assigned to the invitee. Whether it applies is driven by the resolved onboarding role config: when the role enables pay-in (isPayInEnabled), payInIBAN is required — omitting it returns 400 payInIBAN is required when pay-in is enabled for this role. For roles without pay-in, the field is ignored.

SSO programs (client-ref authentication)

Some programs authenticate users through an external IdP and do not have Orenda mint a Cognito identity (e.g. potjestaging). These programs are flagged with usesClientRefAuthentication: true in their program config. When inviting into such a program:
  • clientReference is required — it becomes the invitee’s application identity (and is persisted on the application). Omitting it returns 400 clientReference is required for this program.
  • No Cognito user is created — the user pool lookup, duplicate-email check, and user creation are all skipped.
  • No step-up is needed — SSO callers are step-up exempt, so the confirmation object is not required on this path.
For normal (non-SSO) programs, clientReference is ignored and a Cognito user is created as usual.

Step-up authentication

Every invite is gated by a mandatory step-up: include a confirmation object — either passkey or TOTP. This applies to back-office invites too. For TOTP, the access token must belong to the acting inviter (else 401).
Start a passkey challenge via POST /v1/auth/passkey/challenge to get a passkeySession and fido2options, complete it on the device, then send:
"confirmation": {
  "method": "passkey",
  "passkeySession": "c14102b0-…",
  "assertion": "{\"id\":\"\",\"response\":{…}}"
}
The method is explicit. An incomplete pair (for example totp without accessToken) returns 400; supplying no confirmation returns 422 SCA_MISSING, and no user is created. A pin confirmation is rejected with 422 SCA_INVALID_METHOD. Setting a sub-role flag without an accountId returns 400 accountId is required when inviting a sub-role.

Authorizations

Authorization
string
header
required

Bearer authentication header of the form Bearer <token>, where <token> is your auth token.

x-program-id
string
header
required

The program the request acts on.

Body

application/json

Sent by a signed-in customer inviting a sub-user. Exactly one application flag must be true (isPrepaidCardCustomer / isCardOnly / isSpouse / isChild) — the sub-roles are mutually exclusive, and consumers can only invite sub-role members, never a plain customer. Because a sub-role flag is always set, accountId is always required and must be one of the inviter's own accounts (ACTIVE, not a pseudo account). Must include a confirmation step-up object (passkey or TOTP).

email
string<email>
required
confirmation
Passkey · object
required

Discriminated step-up (SCA) credential. passkey and totp are accepted on this endpoint (a pin confirmation is rejected with 422 SCA_INVALID_METHOD).

firstName
string
lastName
string
dob
string

Date of birth, YYYY-MM-DD.

nationality
string

Alpha-2 country code, e.g. GB.

phone
string

E.164-style number.

address
object
accountId
string<uuid>

Funding parent account the invitee draws against. Required (a sub-role flag is always set on a consumer invite). Must be one of the inviter's own accounts, ACTIVE, and not a pseudo account.

isPrepaidCardCustomer
boolean
isCardOnly
boolean
isSpouse
boolean
isChild
boolean

Response

Invitation processed

success
boolean
Example:

true

data
object