Skip to main content
POST
/
v2
/
consent
/
onboarding

Overview

Creates a new consent set during user onboarding using the onboardingId from the registration flow. This endpoint is typically called after personal details submission and before address submission during the registration flow.
Use the onboardingId returned from email verification (POST /v1/auth/register/email/verify) - do NOT generate a new ID. This links the consent to the user’s registration session.

Use Cases

Mobile App Registration

Collect consent during mobile app onboarding flows

Web Registration

Capture consent on web registration forms

KYC Processes

Record consent during identity verification

Pre-Registration Consent

Collect consent before user account creation

Endpoint

POST https://api.baanx.com/v2/consent/onboarding

Headers

HeaderRequiredDescription
x-client-keyYour public API key
x-secret-keyYour secret API key (keep secure)
Content-TypeMust be application/json
x-us-envSet to true for US region routing
Security: The x-secret-key should only be used in server-side code. Never expose it in client-side applications.

Request Body

Parameters

ParameterTypeRequiredDescription
onboardingIdstringUnique temporary identifier for this onboarding session
tenantIdstringYour tenant identifier (provided by Baanx)
policyTypestringPolicy type: global or US
consentsarrayArray of consent items to record (min 1 item)
metadataobjectAdditional metadata about the consent capture session
FieldTypeRequiredDescription
consentTypestringType of consent (see Consent Types)
consentStatusstringStatus: granted or denied
metadataobjectAdditional context for this specific consent
TypeDescriptionRequired In
eSignActElectronic signature agreement (E-Sign Act compliance)US policy only
termsAndPrivacyTerms of service and privacy policyAll policies
marketingNotificationsMarketing communications opt-inAll policies
smsNotificationsSMS/text message notificationsAll policies
emailNotificationsEmail notificationsAll policies

Metadata Fields (Optional)

FieldTypeDescription
ipAddressstringUser’s IP address at time of consent
userAgentstringBrowser/device user agent string
timestampstringISO 8601 timestamp when consent was captured
clientIdstringClient application identifier
versionstringAPI or app version
Additional custom fields can be included in metadata. All fields must be JSON-serializable.

Examples

US Policy (All 5 Consents)

{
  "onboardingId": "100a99cf-f4d3-4fa1-9be9-2e9828b20ebb",
  "tenantId": "tenant_baanx_prod",
  "policyType": "US",
  "consents": [
    {
      "consentType": "eSignAct",
      "consentStatus": "granted"
    },
    {
      "consentType": "termsAndPrivacy",
      "consentStatus": "granted"
    },
    {
      "consentType": "marketingNotifications",
      "consentStatus": "granted"
    },
    {
      "consentType": "smsNotifications",
      "consentStatus": "denied"
    },
    {
      "consentType": "emailNotifications",
      "consentStatus": "granted"
    }
  ],
  "metadata": {
    "ipAddress": "192.168.1.1",
    "userAgent": "Mozilla/5.0 (iPhone; CPU iPhone OS 14_0 like Mac OS X)",
    "timestamp": "2024-01-15T10:30:00Z",
    "clientId": "mobile-app-ios-v2.1.0"
  }
}

Global Policy (4 Consents, No eSignAct)

{
  "onboardingId": "200b88de-e39c-52e5-8cd9-3f9944b31fcc",
  "tenantId": "tenant_baanx_global",
  "policyType": "global",
  "consents": [
    {
      "consentType": "termsAndPrivacy",
      "consentStatus": "granted"
    },
    {
      "consentType": "marketingNotifications",
      "consentStatus": "granted"
    },
    {
      "consentType": "smsNotifications",
      "consentStatus": "granted"
    },
    {
      "consentType": "emailNotifications",
      "consentStatus": "granted"
    }
  ]
}

Response

201 Created

Success Response:
{
  "consentSetId": "550e8400-e29b-41d4-a716-446655440001",
  "onboardingId": "onboarding_abc123xyz",
  "tenantId": "tenant_baanx_prod",
  "createdAt": "2024-01-15T10:30:00Z",
  "_links": {
    "self": {
      "href": "https://api.baanx.com/v2/consent/consentSet/550e8400-e29b-41d4-a716-446655440001",
      "method": "GET"
    }
  }
}
Response Fields:
FieldTypeDescription
consentSetIdstring (UUID)Generated unique identifier for this consent set
onboardingIdstringYour provided onboarding identifier
tenantIdstringYour tenant identifier
createdAtstring (ISO 8601)Timestamp when consent set was created
_linksobjectHATEOAS links for related resources
Store the consentSetId: You’ll need this to link the user after account creation completes.

400 Bad Request - Missing Required Consents

{
  "error": "Validation error",
  "details": [
    "Missing required consent: termsAndPrivacy for policy type: global"
  ]
}
Cause: Not all required consents for the policy type are present. Required Consents:
  • US Policy: All 5 types (including eSignAct for E-Sign Act compliance)
  • Global Policy: 4 types (excludes eSignAct)
{
  "error": "Validation error",
  "details": [
    "Invalid consentType: 'pushNotifications'. Must be one of: eSignAct, termsAndPrivacy, marketingNotifications, smsNotifications, emailNotifications"
  ]
}
Cause: Using an unsupported consent type.

409 Conflict - Duplicate Onboarding ID

{
  "error": "Conflict",
  "details": [
    "Consent set with onboardingId 'onboarding_abc123' already exists"
  ]
}
Cause: The onboardingId has already been used. Solution: Generate a new unique onboardingId and retry.

498 Invalid Client Key

{
  "error": "Invalid client key",
  "details": [
    "The provided x-client-key is invalid or expired"
  ]
}
Cause: Invalid or expired API credentials.

499 Missing Client Key

{
  "error": "Missing client key",
  "details": [
    "x-client-key header is required for all requests"
  ]
}
Cause: Missing x-client-key header.

Validation Rules

  • Must be the onboardingId from registration email verification
  • Do NOT generate a new ID - use the ID from POST /v1/auth/register/email/verify
  • Format: UUID string (e.g., 100a99cf-f4d3-4fa1-9be9-2e9828b20ebb)
// ✅ Correct: Use onboardingId from registration
const { onboardingId } = await verifyEmail(email, code);
await createConsent(onboardingId, consents);

// ❌ Wrong: Do not generate new ID
// const onboardingId = `onboarding_${uuid()}`;
US Policy requires all 5 consent types (E-Sign Act compliance):
  • eSignAct (required for E-Sign Act compliance)
  • termsAndPrivacy
  • marketingNotifications
  • smsNotifications
  • emailNotifications
Global Policy requires 4 consent types (excludes eSignAct):
  • termsAndPrivacy
  • marketingNotifications
  • smsNotifications
  • emailNotifications
Include these fields for comprehensive audit trails:
metadata: {
  ipAddress: req.ip,
  userAgent: req.headers['user-agent'],
  timestamp: new Date().toISOString(),
  clientId: 'web-app-v1.2.0',
  sessionId: req.session.id,
  privacyPolicyVersion: 'v2.1',
  termsVersion: 'v3.0'
}
All values must be JSON-serializable (no functions, circular references, or undefined).

Code Examples

TypeScript

async function createOnboardingConsent(
  onboardingId: string, // From registration email verification
  consents: Array<{ type: string; status: 'granted' | 'denied' }>,
  userIp: string,
  userAgent: string
) {
  const response = await fetch('https://api.baanx.com/v2/consent/onboarding', {
    method: 'POST',
    headers: {
      'Content-Type': 'application/json',
      'x-client-key': process.env.BAANX_CLIENT_KEY!,
      'x-secret-key': process.env.BAANX_SECRET_KEY!
    },
    body: JSON.stringify({
      onboardingId, // Use ID from registration, don't generate new one
      tenantId: 'tenant_baanx_prod',
      policyType: 'US',
      consents: consents.map(c => ({
        consentType: c.type,
        consentStatus: c.status
      })),
      metadata: {
        ipAddress: userIp,
        userAgent: userAgent,
        timestamp: new Date().toISOString(),
        clientId: 'web-app-v1.2.0'
      }
    })
  });

  if (!response.ok) {
    const error = await response.json();
    throw new Error(`Consent creation failed: ${error.details.join(', ')}`);
  }

  const { consentSetId } = await response.json();
  return consentSetId;
}

// Get onboardingId from registration flow (Step 2)
const { onboardingId } = await verifyEmailCode(email, verificationCode);

// Create consent during registration (Step 4 - before address submission)
const consentSetId = await createOnboardingConsent(
  onboardingId, // From registration
  [
    { type: 'eSignAct', status: 'granted' },
    { type: 'termsAndPrivacy', status: 'granted' },
    { type: 'marketingNotifications', status: 'granted' },
    { type: 'smsNotifications', status: 'denied' },
    { type: 'emailNotifications', status: 'granted' }
  ],
  '192.168.1.1',
  'Mozilla/5.0...'
);

console.log(`Consent set created: ${consentSetId}`);

Python

import requests
from datetime import datetime

def create_onboarding_consent(onboarding_id, consents, user_ip, user_agent):
    """Create consent using onboardingId from registration flow"""
    response = requests.post(
        'https://api.baanx.com/v2/consent/onboarding',
        headers={
            'Content-Type': 'application/json',
            'x-client-key': os.getenv('BAANX_CLIENT_KEY'),
            'x-secret-key': os.getenv('BAANX_SECRET_KEY')
        },
        json={
            'onboardingId': onboarding_id,  # From registration, don't generate new
            'tenantId': 'tenant_baanx_prod',
            'policyType': 'US',
            'consents': [
                {'consentType': c['type'], 'consentStatus': c['status']}
                for c in consents
            ],
            'metadata': {
                'ipAddress': user_ip,
                'userAgent': user_agent,
                'timestamp': datetime.utcnow().isoformat() + 'Z',
                'clientId': 'web-app-v1.2.0'
            }
        }
    )

    response.raise_for_status()
    data = response.json()

    return data['consentSetId']

# Get onboardingId from registration flow (Step 2)
onboarding_id = verify_email_code(email, verification_code)['onboardingId']

# Create consent during registration (Step 4 - before address submission)
consent_set_id = create_onboarding_consent(
    onboarding_id,  # From registration
    [
        {'type': 'eSignAct', 'status': 'granted'},
        {'type': 'termsAndPrivacy', 'status': 'granted'},
        {'type': 'marketingNotifications', 'status': 'granted'},
        {'type': 'smsNotifications', 'status': 'denied'},
        {'type': 'emailNotifications', 'status': 'granted'}
    ],
    '192.168.1.1',
    'Mozilla/5.0...'
)

print(f"Consent set created: {consent_set_id}")

cURL

curl -X POST https://api.baanx.com/v2/consent/onboarding \
  -H "Content-Type: application/json" \
  -H "x-client-key: your_client_key" \
  -H "x-secret-key: your_secret_key" \
  -d '{
    "onboardingId": "100a99cf-f4d3-4fa1-9be9-2e9828b20ebb",
    "tenantId": "tenant_baanx_prod",
    "policyType": "US",
    "consents": [
      {
        "consentType": "eSignAct",
        "consentStatus": "granted"
      },
      {
        "consentType": "termsAndPrivacy",
        "consentStatus": "granted"
      },
      {
        "consentType": "marketingNotifications",
        "consentStatus": "granted"
      },
      {
        "consentType": "smsNotifications",
        "consentStatus": "denied"
      },
      {
        "consentType": "emailNotifications",
        "consentStatus": "granted"
      }
    ],
    "metadata": {
      "ipAddress": "192.168.1.1",
      "userAgent": "Mozilla/5.0...",
      "timestamp": "2024-01-15T10:30:00Z",
      "clientId": "web-app-v1.2.0"
    }
  }'

Next Steps

After creating the consent set:
  1. Store the consentSetId: You’ll need it to link the user later
  2. Complete user registration: Finalize account creation in your system
  3. Link user to consent: Call Link User to Consent Set