> ## Documentation Index
> Fetch the complete documentation index at: https://developer.fin.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Onboarding Individual Customers

> Complete guide to onboarding individual customers with personal details, financial profiles, and identity verification

<Tabs>
  <Tab title="V2 (Latest)">
    Onboard individual customers to enable cross-border payments and payouts through Fin.com's platform. This guide walks you through creating individual customer profiles, uploading verification documents, and managing the compliance workflow using the **V2 API**.

    ## Prerequisites

    Before you begin, ensure you have:

    * **API credentials**: Client ID and secret from the [API Keys](https://orchestration.fin.com/api-keys) section
    * **Access token**: Generated via [POST /v1/oauth/token](/api-reference/authentication/issue-a-token)
    * **Catalogue data**: Familiarity with [/v1/occupations](/api-reference/catalogue/list-occupations), [/v1/purposes](/api-reference/catalogue/list-account-purposes), and [/v1/source-of-funds](/api-reference/catalogue/list-source-of-funds) endpoints

    ## Onboarding Steps

    | Step                    | Endpoint                                                                                                                                                                                                                                       | Description                                                     |
    | ----------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | --------------------------------------------------------------- |
    | 1. Fetch Catalogue Data | [GET /v1/occupations](/api-reference/catalogue/list-occupations), [GET /v1/purposes?type=INDIVIDUAL](/api-reference/catalogue/list-account-purposes), [GET /v1/source-of-funds?type=INDIVIDUAL](/api-reference/catalogue/list-source-of-funds) | Retrieve valid IDs for occupations, purposes, and fund sources  |
    | 2. Create Customer      | [POST /v2/customers/individual](/api-reference/customers/create-individual-customer-v2)                                                                                                                                                        | Submit personal details, address, and financial profile         |
    | 3. Upload Documents     | [POST /v1/customers/upload](/api-reference/customers/upload-document)                                                                                                                                                                          | Upload identity, selfie, and address proof files                |
    | 4. Attach Documents     | Link uploaded documents to the customer (processed asynchronously)                                                                                                                                                                             |                                                                 |
    | 5. Monitor Status       | Webhooks: `customer.status`                                                                                                                                                                                                                    | Track verification progress (INCOMPLETE → REVIEWING → APPROVED) |

    ***

    ## Request Body Structure

    ### Verification Type (Required)

    > **Verification type** determines how customer identity is validated. **STANDARD** uses traditional document verification. On **RELIANCE**, Fin.com relies on your KYC. Please contact our compliance team to know more.

    ```json theme={null}
    {
      "verification_type": "STANDARD"
    }
    ```

    <Warning>
      **RELIANCE verification** must be explicitly enabled for your client. If not available, you'll receive a 423 error with the message: `"RELIANCE is not available for your client"`
    </Warning>

    ### Basic Information (Required)

    > Personal details exactly as shown on identity documents. **All fields must use only English (Latin) characters**. If any field contains non-ASCII characters, provide a transliterated value in the corresponding `_en` field.

    **Fields:**

    | Field                   | Type           | Required    | Description                                                                       | Example                      |
    | ----------------------- | -------------- | ----------- | --------------------------------------------------------------------------------- | ---------------------------- |
    | `first_name`            | string         | Yes         | Legal first name as shown on ID                                                   | `"María"`                    |
    | `first_name_en`         | string         | Conditional | English transliteration. Required if `first_name` contains non-ASCII characters.  | `"Maria"`                    |
    | `middle_name`           | string         | No          | Middle name                                                                       | `"Elena"`                    |
    | `middle_name_en`        | string         | Conditional | English transliteration. Required if `middle_name` contains non-ASCII characters. | `"Elena"`                    |
    | `last_name`             | string         | Yes         | Legal last name as shown on ID                                                    | `"García"`                   |
    | `last_name_en`          | string         | Conditional | English transliteration. Required if `last_name` contains non-ASCII characters.   | `"Garcia"`                   |
    | `dob`                   | string (date)  | Yes         | Date of birth in YYYY-MM-DD format. Age must be between 18 and 120.               | `"1990-04-15"`               |
    | `email`                 | string (email) | Yes         | Personal email address - **must be all lowercase**                                | `"maria.garcia@example.com"` |
    | `phone`                 | string         | Yes         | Phone number in E.164 format                                                      | `"+14155552671"`             |
    | `country_of_residence`  | string         | Yes         | ISO Alpha-3 country code where person resides                                     | `"USA"`                      |
    | `primary_nationality`   | string         | Yes         | ISO Alpha-3 country code of primary citizenship                                   | `"USA"`                      |
    | `secondary_nationality` | string         | No          | ISO Alpha-3 country code of secondary citizenship                                 | `"MEX"`                      |
    | `gender`                | string         | No          | `MALE` or `FEMALE`                                                                | `"FEMALE"`                   |
    | `tax_info`              | array          | Yes         | Tax identification documents (see below)                                          | --                           |

    <Warning>
      Email must be **all lowercase** or validation will fail. Convert to lowercase before sending: `maria.garcia@example.com` ✓ not `Maria.Garcia@Example.com` ✗
    </Warning>

    ***

    #### Tax Info Array

    Each entry in `tax_info` must have a unique `document_id`.

    | Field           | Type   | Required | Description                            | Example         |
    | --------------- | ------ | -------- | -------------------------------------- | --------------- |
    | `country_code`  | string | Yes      | ISO Alpha-3 country code               | `"USA"`         |
    | `document_type` | string | Yes      | Tax document type (e.g., `SSN`, `TIN`) | `"SSN"`         |
    | `document_id`   | string | Yes      | Tax identification number              | `"123-45-6789"` |

    <Tip>
      **TIN Format by Country:**

      * **USA**: Social Security Number in format `xxx-xx-xxxx` (e.g., `123-45-6789`)
      * **Other countries**: Must use the country's official Tax Identification Number format
    </Tip>

    <Note>
      **V2 Change: `tax_info` replaces `tin`**. V1 used a single `tin` string field. V2 uses a `tax_info` array, which supports multiple tax documents across different countries.
    </Note>

    **Example:**

    ```json theme={null}
    {
      "basic_info": {
        "first_name": "Maria",
        "middle_name": "Elena",
        "last_name": "Garcia",
        "dob": "1990-04-15",
        "email": "maria.garcia@example.com",
        "phone": "+14155552671",
        "country_of_residence": "USA",
        "primary_nationality": "USA",
        "secondary_nationality": "MEX",
        "gender": "FEMALE",
        "tax_info": [
          {
            "country_code": "USA",
            "document_type": "SSN",
            "document_id": "123-45-6789"
          }
        ]
      }
    }
    ```

    ***

    ### Address (Required)

    > Current residential address of the customer. The `country` field **must match** `basic_info.country_of_residence`.

    **Fields:**

    | Field              | Type   | Required    | Description                                                                         | Example               |
    | ------------------ | ------ | ----------- | ----------------------------------------------------------------------------------- | --------------------- |
    | `street_line_1`    | string | Yes         | Primary street address                                                              | `"123 Market Street"` |
    | `street_line_1_en` | string | Conditional | English transliteration. Required if `street_line_1` contains non-ASCII characters. | `"123 Market Street"` |
    | `street_line_2`    | string | No          | Apartment, suite, unit, etc.                                                        | `"Apt 4B"`            |
    | `street_line_2_en` | string | Conditional | English transliteration. Required if `street_line_2` contains non-ASCII characters. | `"Apt 4B"`            |
    | `city`             | string | Yes         | City name                                                                           | `"San Francisco"`     |
    | `subdivision_code` | string | Yes         | ISO 3166-2 subdivision code                                                         | `"US-CA"`             |
    | `postal_code`      | string | Yes         | Postal or ZIP code                                                                  | `"94103"`             |
    | `country`          | string | Yes         | ISO Alpha-3 country code. **Must match `country_of_residence`.**                    | `"USA"`               |

    <Tip>
      **Subdivision Code Format**: Use ISO 3166-2 codes from the catalogue API. For example, use `US-CA` instead of `CA` for California, or `GB-ENG` instead of `England`. Fetch valid codes from [/v1/countries/](/api-reference/catalogue/list-subdivision-codes-—-iso-3166-1-alpha-2){country_code}[/subdivisions](/api-reference/catalogue/list-subdivision-codes-—-iso-3166-1-alpha-2).
    </Tip>

    <Tip>
      **V2 Change: Address fields**. V1 used a single `street` field. V2 splits this into `street_line_1` and `street_line_2`. The `state` field has been renamed to `subdivision_code`.
    </Tip>

    **Example:**

    ```json theme={null}
    {
      "address": {
        "street_line_1": "123 Market Street",
        "street_line_2": "Apt 4B",
        "city": "San Francisco",
        "subdivision_code": "US-CA",
        "postal_code": "94103",
        "country": "USA"
      }
    }
    ```

    ***

    ### Financial Profile (Required)

    > Describes employment status, occupation, transaction purpose, volume, and fund sources. Use catalogue endpoints to fetch valid IDs.

    **Fields:**

    | Field                         | Type       | Required | Description                                                              | How to Get Value                                                                         |
    | ----------------------------- | ---------- | -------- | ------------------------------------------------------------------------ | ---------------------------------------------------------------------------------------- |
    | `employment_status`           | string     | Yes      | One of: `EMPLOYED`, `SELF_EMPLOYED`, `RETIRED`, `STUDENT`, `UNEMPLOYED`  | Select from enum                                                                         |
    | `occupation_id`               | integer    | Yes      | Customer's occupation                                                    | [GET /v1/occupations](/api-reference/catalogue/list-occupations)                         |
    | `purpose_id`                  | integer    | Yes      | Purpose of using the service                                             | [GET /v1/purposes?type=INDIVIDUAL](/api-reference/catalogue/list-account-purposes)       |
    | `purpose_remarks`             | string     | No       | Free-text description of the purpose                                     | User input                                                                               |
    | `source_of_fund_ids`          | integer\[] | Yes      | Source(s) of funds (supports multiple)                                   | [GET /v1/source-of-funds?type=INDIVIDUAL](/api-reference/catalogue/list-source-of-funds) |
    | `source_of_funds_description` | string     | No       | Free-text description of fund sources                                    | User input                                                                               |
    | `monthly_volume_usd`          | integer    | Yes      | Expected monthly transaction volume in **USD** (not cents). Accepts `0`. | User estimate: `5000`                                                                    |

    <Note>
      When fetching catalogue data for individual customers, use the `?type=INDIVIDUAL` query parameter to get the correct options for `purpose_id` and `source_of_fund_ids`.
    </Note>

    <Tip>
      **V2 Change: Multiple fund sources**. V1 accepted a single `source_of_fund_id` integer. V2 uses `source_of_fund_ids` as an array, allowing multiple sources. V2 also adds `employment_status` (required), `purpose_remarks`, and `source_of_funds_description`.
    </Tip>

    **Example:**

    ```json theme={null}
    {
      "financial_profile": {
        "employment_status": "EMPLOYED",
        "occupation_id": 42,
        "purpose_id": 3,
        "purpose_remarks": "Personal remittances to family",
        "source_of_fund_ids": [1, 5],
        "source_of_funds_description": "Monthly salary from employment",
        "monthly_volume_usd": 5000
      }
    }
    ```

    ***

    ### Metadata (Optional)

    Custom key-value pairs for internal tracking:

    ```json theme={null}
    {
      "meta_data": {
        "reference": "client-ref-abc-001"
      }
    }
    ```

    ***

    ## Document Upload & Attachment

    After creating the individual customer, you must upload and attach verification documents.

    ### Step 1: Upload Documents

    Upload files using multipart/form-data:

    ```bash theme={null}
    curl --request POST \
      --url https://sandbox.api.fin.com/v1/customers/upload \
      --header 'Authorization: Bearer <YOUR_ACCESS_TOKEN>' \
      --header 'Content-Type: multipart/form-data' \
      --form 'customer_id=55bd6b4e-c20a-4cc8-9535-91d5557a67d9' \
      --form 'file1=@/path/to/selfie.jpg' \
      --form 'file2=@/path/to/license_front.pdf' \
      --form 'file3=@/path/to/license_back.pdf' \
      --form 'file4=@/path/to/bank_statement.pdf'
    ```

    **Allowed file types**: PDF, JPG, JPEG, PNG

    **Response:**

    ```json theme={null}
    {
      "data": {
        "files": [
          {"file1": "/AbAcQ4hn_0652746727637.pdf"},
          {"file2": "/AbAcQ4hn_0652746727638.pdf"},
          {"file3": "/XyZ123mn_0652746727639.pdf"},
          {"file4": "/PoAdef45_0652746727640.pdf"}
        ]
      }
    }
    ```

    Save these URIs - you'll use them in the attachment request.

    ***

    ### Step 2: Attach Documents

    In V2, the `customer_id` moves to the URL path. The request body uses `identifying_documents` and `address_documents` arrays instead of V1's `proof_of_identity` and `proof_of_address` objects.

    <Note>
      * The customer must be in `INCOMPLETE` or `ACTION_REQUIRED` status. Only one attach request can be in flight per customer. A second concurrent request returns `409`.
      * The `tos_policies_value` should be parsed from the `tos_policies_url` query parameter returned when creating the customer. Providing this value signifies that the customer was shown the terms and accepted them.
    </Note>

    ```bash theme={null}
    curl --request POST \
      --url https://sandbox.api.fin.com/v2/customers/55bd6b4e-c20a-4cc8-9535-91d5557a67d9/individual/attach \
      --header 'Authorization: Bearer <YOUR_ACCESS_TOKEN>' \
      --header 'Content-Type: application/json' \
      --data '{
      "identifying_documents": [
        {
          "type": "SELFIE",
          "files": [
            {"uri": "/AbAcQ4hn_0652746727637.pdf"}
          ]
        },
        {
          "type": "DRIVERS_LICENSE",
          "number": "DL987654321",
          "country": "USA",
          "state": "US-CA",
          "issue_date": "2019-06-01",
          "expiry_date": "2029-06-01",
          "files": [
            {"side": "FRONT", "uri": "/AbAcQ4hn_0652746727638.pdf"},
            {"side": "BACK", "uri": "/XyZ123mn_0652746727639.pdf"}
          ]
        }
      ],
      "address_documents": [
        {
          "type": "BANK_STATEMENT",
          "country": "USA",
          "files": [
            {"uri": "/PoAdef45_0652746727640.pdf"}
          ]
        }
      ],
     "tos_policies_value": "e9414388-fbdf-4407-b5c2-bc39eae3645b"
    }'
    ```

    **Response (200 - queued for async processing):**

    ```json theme={null}
    {
      "data": {
        "customer_id": "55bd6b4e-c20a-4cc8-9535-91d5557a67d9"
      },
      "meta": null
    }
    ```

    <Warning>
      V2 document attachment is **asynchronous**. A `200` response means the request is validated and queued, not that processing is complete. Listen for `customer.status` webhooks to track progress.
    </Warning>

    #### Identity Document Types & Side Requirements

    | Type               | Files | Sides Required           | `state` field                                    |
    | ------------------ | ----- | ------------------------ | ------------------------------------------------ |
    | `PASSPORT`         | 1     | Optional                 | Forbidden                                        |
    | `NATIONAL_ID`      | 2     | One `FRONT` + one `BACK` | Forbidden                                        |
    | `DRIVERS_LICENSE`  | 2     | One `FRONT` + one `BACK` | Required if country is `USA`, optional otherwise |
    | `RESIDENCE_PERMIT` | 2     | One `FRONT` + one `BACK` | Forbidden                                        |
    | `SELFIE`           | 1     | Optional                 | N/A                                              |

    <Note>
      At most **one non-SELFIE** identity document may be included per request. A `SELFIE` entry may be required depending on your client configuration. When required, include exactly one `SELFIE` entry with at least one file.
    </Note>

    #### Address Proof Types

    | Type                | Description                                |
    | ------------------- | ------------------------------------------ |
    | `UTILITY_BILL`      | Recent utility bill (gas, electric, water) |
    | `BANK_STATEMENT`    | Bank statement (within the last 3 months)  |
    | `GOVERNMENT_LETTER` | Official government correspondence         |

    Exactly **one** `address_documents` entry is required. The `country` on the address document must match the customer's `country_of_residence`.

    <Tip>
      **Proof of Address Requirements:**

      * Document must show the customer's **full name** and **complete address**
      * Address must match the `address` provided in the customer creation request
      * Document should be issued within the **last 90 days** (for utility bills, bank statements, and government letters)
    </Tip>

    #### Key Rules

    * File URIs must be **unique** across the entire reques and must belong to this customer.
    * `expiry_date` is required for all identity document types except `SELFIE` and must be in the future.

    ***

    ## Customer Status & Webhooks

    After document submission, customers go through a verification workflow:

    **Status Lifecycle:**

    <Frame>
      <img src="https://mintcdn.com/fincom/7n-7PW9mg2_I4Tw7/images/individual-status-lifecycle.png?fit=max&auto=format&n=7n-7PW9mg2_I4Tw7&q=85&s=ee017bf1c05124a074dd17da4255b49c" alt="Individual Status Lifecycle" width="1440" height="1504" data-path="images/individual-status-lifecycle.png" />
    </Frame>

    | Status            | Description                                                    |
    | ----------------- | -------------------------------------------------------------- |
    | `INCOMPLETE`      | Customer created but documents not yet attached                |
    | `REVIEWING`       | Documents submitted and under compliance review                |
    | `APPROVED`        | Verification complete, customer can transact                   |
    | `ACTION_REQUIRED` | Additional documents or corrections needed (re-attach allowed) |
    | `ON_HOLD`         | Additional information required via RFI                        |
    | `REJECTED`        | Verification failed, see rejection reason                      |

    **Webhook Events:**

    * `customer.created` - Fired when a customer is created
    * `customer.status` - Fired when status changes

    Subscribe to webhooks to automate your onboarding flow. See [Verifying Webhooks](/guides/webhooks/verifying-webhooks) for setup.

    ***

    ## Error Response Examples

    **Email validation error (not lowercase):**

    ```json theme={null}
    {
      "message": "Validation failed",
      "errors": {
        "basic_info.email": ["Email must be all lowercase"]
      }
    }
    ```

    **RELIANCE not enabled:**

    ```json theme={null}
    {
      "message": "RELIANCE is not available for your client"
    }
    ```

    **Address country mismatch:**

    ```json theme={null}
    {
      "message": "Validation failed",
      "errors": {
        "address.country": ["Must match basic_info.country_of_residence"]
      }
    }
    ```

    **Concurrent attach conflict (409):**

    ```json theme={null}
    {
      "error": {
        "code": "conflict",
        "message": "An attach request is already in progress for this customer"
      }
    }
    ```

    **Customer not eligible for attach (403):**

    ```json theme={null}
    {
      "error": {
        "code": "forbidden",
        "message": "Customer is not eligible for this operation"
      }
    }
    ```

    ***

    ## What's Next?

    You've successfully created an individual customer using V2. Here's what to do next:

    ### 1. Monitor Verification Status

    Listen for webhook events to track verification progress:

    * Subscribe to `customer.created` and `customer.status` webhooks
    * Handle status transitions: `INCOMPLETE` → `REVIEWING` → `APPROVED`
    * For `ACTION_REQUIRED` statuses, re-submit corrected documents via the attach endpoint
    * For `ON_HOLD` statuses, respond to RFIs (Requests for Information) via email or Slack with additional documents
    * See [Webhook Verification](/guides/webhooks/verifying-webhooks) for implementation details

    ### 2. Test Edge Cases

    Validate your integration handles common errors:

    * ✓ Email with uppercase characters
    * ✓ `address.country` not matching `country_of_residence`
    * ✓ Non-ASCII characters without `_en` transliteration fields
    * ✓ Missing required fields
    * ✓ RELIANCE verification when not enabled
    * ✓ Concurrent attach requests (409)
    * ✓ Expired identity documents
    * ✓ Duplicate file URIs across documents

    ### 3. Production Checklist

    Before going live, ensure you have:

    * Implemented webhook handling for status updates
    * Added proper error handling for all failure scenarios (400, 401, 403, 409, 422)
    * Client-side validation for email lowercase and tax document format
    * Fetched and cached catalogue data (occupations, purposes, source-of-funds)
    * Implemented document upload UI/flow including selfie capture
    * Set up monitoring for failed verifications
    * Tested the complete workflow end-to-end

    ### 4. Create Beneficiaries

    Once your individual customer is approved, you can create beneficiaries for payouts:

    * See [Beneficiary Account Validation](/api-reference/beneficiaries/account-info-validation)
    * Review [Beneficiary Relationships](/api-reference/beneficiaries/relationships)

    ***

    ## V1 to V2 Migration Summary

    | Area                 | V1                                     | V2                                                                   |
    | -------------------- | -------------------------------------- | -------------------------------------------------------------------- |
    | Create endpoint      | `POST /v1/customers/individual`        | `POST /v2/customers/individual`                                      |
    | `verification_type`  | Optional (defaults to STANDARD)        | Required                                                             |
    | Name fields          | `first_name`, `last_name`              | Adds `middle_name` + `_en` transliteration fields                    |
    | Nationality          | `nationality`                          | `primary_nationality` + optional `secondary_nationality`             |
    | Gender               | Not supported                          | Optional `gender` field                                              |
    | Tax ID               | Single `tin` string                    | `tax_info` array with `country_code`, `document_type`, `document_id` |
    | Address street       | Single `street` field                  | `street_line_1` + `street_line_2` + `_en` fields                     |
    | Address state        | `state`                                | `subdivision_code`                                                   |
    | Address country      | No validation against residence        | Must match `country_of_residence`                                    |
    | Employment           | Not supported                          | Required `employment_status` enum                                    |
    | Source of funds      | Single `source_of_fund_id`             | Array `source_of_fund_ids` + `source_of_funds_description`           |
    | Purpose              | `purpose_id` only                      | `purpose_id` + optional `purpose_remarks`                            |
    | Attach endpoint      | `POST /v1/customers/individual/attach` | `POST /v2/customers/{customer_id}/individual/attach`                 |
    | Attach body          | `customer_id` in body                  | `customer_id` in URL path                                            |
    | Identity docs        | `proof_of_identity` object             | `identifying_documents` array                                        |
    | Address docs         | `proof_of_address` object              | `address_documents` array (max 1 entry)                              |
    | Selfie               | Not supported                          | `SELFIE` type in `identifying_documents`                             |
    | Residence permit     | Not supported as ID type               | `RESIDENCE_PERMIT` type supported                                    |
    | Address proof types  | 8 types                                | 3 types: `UTILITY_BILL`, `BANK_STATEMENT`, `GOVERNMENT_LETTER`       |
    | `tos_policies_value` | Required in attach body                | Not required in attach body                                          |
    | Processing           | Synchronous                            | Asynchronous (200 = queued)                                          |
    | Concurrency          | No guard                               | 409 if attach already in flight                                      |

    ***

    ## Common Pitfalls & Solutions

    | Pitfall                               | Solution                                                                                                               |
    | ------------------------------------- | ---------------------------------------------------------------------------------------------------------------------- |
    | **Email validation fails**            | Ensure email is **all lowercase** before sending: `maria.garcia@example.com` ✓ not `Maria.Garcia@Example.com` ✗        |
    | **Address country mismatch**          | `address.country` must exactly match `basic_info.country_of_residence`.                                                |
    | **RELIANCE 423 error**                | RELIANCE verification must be enabled for your client. Contact support or use `STANDARD`.                              |
    | **Non-ASCII without `_en` field**     | If name or address contains non-Latin characters, provide the transliterated value in the `_en` counterpart field.     |
    | **Subdivision code validation fails** |                                                                                                                        |
    | **Phone format rejected**             | Use E.164 format with country code: `+14155552671`, not `(415) 555-2671`.                                              |
    | **Monthly volume rejected**           | Provide amount in USD as integer (not cents): `5000` for \$5,000, not `500000`.                                        |
    | **Missing document sides**            | For `NATIONAL_ID`, `DRIVERS_LICENSE`, and `RESIDENCE_PERMIT`, include both `FRONT` and `BACK` files.                   |
    | **Concurrent attach fails (409)**     | Only one attach per customer at a time. Wait for the first to complete before retrying.                                |
    | **Expired identity document**         | `expiry_date` must be in the future. Ensure documents are not expired before submitting.                               |
    | **Selfie missing**                    | If your client requires selfie, include exactly one `SELFIE` entry in `identifying_documents`.                         |
    | **Duplicate file URIs**               | File URIs must be unique across the request (SELFIE excluded). Don't reuse the same URI for identity and address docs. |
  </Tab>

  <Tab title="V1">
    Onboard individual customers to enable cross-border payments and payouts through Fin.com's platform. This guide walks you through creating individual customer profiles, uploading verification documents, and managing the compliance workflow.

    ## Prerequisites

    Before you begin, ensure you have:

    * **API credentials**: Client ID and secret from the [API Keys](https://orchestration.fin.com/api-keys) section
    * **Access token**: Generated via [POST /v1/oauth/token](/api-reference/authentication/issue-a-token)
    * **Catalogue data**: Familiarity with [/v1/occupations](/api-reference/catalogue/list-occupations), [/v1/purposes](/api-reference/catalogue/list-account-purposes), and [/v1/source-of-funds](/api-reference/catalogue/list-source-of-funds) endpoints

    ## Onboarding Steps

    | Step                    | Endpoint                                                                                                                                                                                                                                       | Description                                                     |
    | ----------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | --------------------------------------------------------------- |
    | 1. Fetch Catalogue Data | [GET /v1/occupations](/api-reference/catalogue/list-occupations), [GET /v1/purposes?type=INDIVIDUAL](/api-reference/catalogue/list-account-purposes), [GET /v1/source-of-funds?type=INDIVIDUAL](/api-reference/catalogue/list-source-of-funds) | Retrieve valid IDs for occupations, purposes, and fund sources  |
    | 2. Create Customer      | [POST /v1/customers/individual](/api-reference/customers/create-individual-customer)                                                                                                                                                           | Submit personal details, address, and financial profile         |
    | 3. Upload Documents     | [POST /v1/customers/upload](/api-reference/customers/upload-document)                                                                                                                                                                          | Upload identity and address proof files                         |
    | 4. Attach Documents     | [POST /v1/customers/individual/attach](/api-reference/customers/attach-documents-to-individual-customer)                                                                                                                                       | Link uploaded documents to customer with TOS acceptance         |
    | 5. Monitor Status       | Webhooks: `customer.status`                                                                                                                                                                                                                    | Track verification progress (INCOMPLETE → REVIEWING → APPROVED) |

    ***

    ## Request Body Structure

    #### Verification Type (Optional)

    > **Verification type** determines how customer identity is validated. **STANDARD** uses traditional document verification (default). **RELIANCE** leverages third-party KYC data when enabled for your client.

    ```json theme={null}
    {
      "verification_type": "STANDARD"
    }
    ```

    The `verification_type` field is optional and defaults to `STANDARD` if omitted.

    <Warning>
      **RELIANCE verification** must be explicitly enabled for your client. If not available, you'll receive a 423 error with message: `"RELIANCE is not available for your client"`
    </Warning>

    #### Basic Information (Required)

    > Personal details exactly as shown on identity documents. **All fields must use only English (Latin) characters**.

    **Fields:**

    | Field                  | Type           | Description                                        | Example                  |
    | ---------------------- | -------------- | -------------------------------------------------- | ------------------------ |
    | `first_name`           | string         | Legal first name as shown on ID                    | `"John"`                 |
    | `last_name`            | string         | Legal last name as shown on ID                     | `"Doe"`                  |
    | `dob`                  | string (date)  | Date of birth in YYYY-MM-DD format                 | `"1990-01-15"`           |
    | `email`                | string (email) | Personal email address - **must be all lowercase** | `"john.doe@example.com"` |
    | `phone`                | string         | Phone number in E.164 format                       | `"+14155552671"`         |
    | `country_of_residence` | string         | ISO Alpha-3 country code where person resides      | `"USA"`                  |
    | `nationality`          | string         | ISO Alpha-3 country code of citizenship            | `"USA"`                  |
    | `tin`                  | string         | Tax Identification Number                          | `"123-45-6789"`          |

    <Warning>
      Email must be **all lowercase** or validation will fail. Convert to lowercase before sending: `john.doe@example.com` ✓ not `John.Doe@Example.com` ✗
    </Warning>

    <Tip>
      **TIN Format by Country:**

      * **USA**: Social Security Number in format `xxx-xx-xxxx` (e.g., `123-45-6789`)
      * **Other countries**: Must use the country's official Tax Identification Number format
    </Tip>

    **Example:**

    ```json theme={null}
    {
      "basic_info": {
        "first_name": "John",
        "last_name": "Doe",
        "dob": "1990-01-15",
        "email": "john.doe@example.com",
        "phone": "+14155552671",
        "country_of_residence": "USA",
        "nationality": "USA",
        "tin": "123-45-6789"
      }
    }
    ```

    #### Address (Required)

    > Current residential address of the customer. This must match the address on proof of address documents.

    **Fields:**

    | Field         | Type   | Description                                         | Example                    |
    | ------------- | ------ | --------------------------------------------------- | -------------------------- |
    | `street`      | string | Full street address including apartment/unit number | `"123 Main Street Apt 4B"` |
    | `city`        | string | City name                                           | `"San Francisco"`          |
    | `state`       | string | `"US-CA"`                                           |                            |
    | `postal_code` | string | Postal or ZIP code                                  | `"94103"`                  |
    | `country`     | string | ISO Alpha-3 country code                            | `"USA"`                    |

    <Tip>
      **State Code Format**: Use subdivision codes from the catalogue API, not abbreviations. For example, use `US-CA` instead of `CA` for California, or `GB-ENG` instead of `England`.
    </Tip>

    **Example:**

    ```json theme={null}
    {
      "address": {
        "street": "123 Main Street Apt 4B",
        "city": "San Francisco",
        "state": "US-CA",
        "postal_code": "94103",
        "country": "USA"
      }
    }
    ```

    #### Financial Profile (Required)

    > Describes occupation, transaction purpose, volume, and fund sources. Use catalogue endpoints to fetch valid IDs.

    **Fields:**

    | Field                | Type    | Description                                                              | How to Get Value                                                                         |
    | -------------------- | ------- | ------------------------------------------------------------------------ | ---------------------------------------------------------------------------------------- |
    | `occupation_id`      | integer | Customer's occupation                                                    | [GET /v1/occupations](/api-reference/catalogue/list-occupations)                         |
    | `source_of_fund_id`  | integer | Source of funds                                                          | [GET /v1/source-of-funds?type=INDIVIDUAL](/api-reference/catalogue/list-source-of-funds) |
    | `purpose_id`         | integer | Purpose of using the service                                             | [GET /v1/purposes?type=INDIVIDUAL](/api-reference/catalogue/list-account-purposes)       |
    | `monthly_volume_usd` | integer | Expected monthly transaction volume in **USD** (not cents). Accepts `0`. | User estimate: `5000`                                                                    |

    <Note>
      When fetching catalogue data for individual customers, use the `?type=INDIVIDUAL` query parameter to get the correct options for `source_of_fund_id` and `purpose_id`.
    </Note>

    **Example:**

    ```json theme={null}
    {
      "financial_profile": {
        "occupation_id": 1,
        "source_of_fund_id": 1,
        "purpose_id": 1,
        "monthly_volume_usd": 5000
      }
    }
    ```

    In this example: `occupation_id: 1` = Software Engineer, `source_of_fund_id: 1` = Employment income, `purpose_id: 1` = Personal remittance, `monthly_volume_usd: 5000` = \$5,000 USD per month.

    #### Metadata (Optional)

    Custom key-value pairs for internal tracking:

    ```json theme={null}
    {
      "meta_data": {
        "customer_reference": "REF-20250123-JOHN",
        "internal_notes": "Premium tier customer",
        "referral_code": "FRIEND2025"
      }
    }
    ```

    ### Document Upload & Attachment

    After creating the individual customer, you must upload and attach verification documents.

    #### Step 1: Upload Documents

    Upload files using multipart/form-data:

    ```bash theme={null}
    curl --request POST \
      --url https://sandbox.api.fin.com/v1/customers/upload \
      --header 'Authorization: Bearer <YOUR_ACCESS_TOKEN>' \
      --header 'Content-Type: multipart/form-data' \
      --form 'customer_id=55bd6b4e-c20a-4cc8-9535-91d5557a67d9' \
      --form 'file1=@/path/to/passport_front.pdf' \
      --form 'file2=@/path/to/utility_bill.pdf'
    ```

    **Allowed file types**: PDF, JPG, JPEG, PNG

    **Response:**

    ```json theme={null}
    {
      "data": {
        "files": [
          {"file1": "/AbAcQ4hn_0652746727637.pdf"},
          {"file2": "/XyZ123mn_0652746727638.pdf"}
        ]
      }
    }
    ```

    Save these URIs - you'll use them in the attachment request.

    #### Step 2: Attach Documents

    Link identity and address proof documents to the customer:

    ```bash theme={null}
    curl --request POST \
      --url https://sandbox.api.fin.com/v1/customers/individual/attach \
      --header 'Authorization: Bearer <YOUR_ACCESS_TOKEN>' \
      --header 'Content-Type: application/json' \
      --data '{
      "customer_id": "55bd6b4e-c20a-4cc8-9535-91d5557a67d9",
      "proof_of_identity": {
        "type": "PASSPORT",
        "number": "A12345678",
        "country": "USA",
        "issue_date": "2020-01-15",
        "expiry_date": "2030-01-15",
        "files": [
          {"uri": "/AbAcQ4hn_0652746727637.pdf"}
        ]
      },
      "proof_of_address": {
        "type": "UTILITY_BILL",
        "country": "USA",
        "files": [
          {"uri": "/XyZ123mn_0652746727638.pdf"}
        ]
      },
      "tos_policies_value": "e9414388-fbdf-4407-b5c2-bc39eae3645b"
    }'
    ```

    <Note>
      The `tos_policies_value` should be parsed from the `tos_policies_url` query parameter returned when creating the customer. Providing this value signifies that the customer was shown the terms and accepted them.
    </Note>

    <Warning>
      For `NATIONAL_ID` and `DRIVERS_LICENSE`, you **must** provide both `FRONT` and `BACK` images using the `side` field. For `PASSPORT`, the `side` field is optional.
    </Warning>

    **Example with National ID (requires front and back):**

    ```json theme={null}
    {
      "proof_of_identity": {
        "type": "NATIONAL_ID",
        "number": "A12345678",
        "country": "USA",
        "issue_date": "2020-01-15",
        "expiry_date": "2030-01-15",
        "files": [
          {"side": "FRONT", "uri": "/id_front_0652746727640.pdf"},
          {"side": "BACK", "uri": "/id_back_0652746727641.pdf"}
        ]
      }
    }
    ```

    **Identity Document Types:**

    | Type              | Description      | Side Required      |
    | ----------------- | ---------------- | ------------------ |
    | `PASSPORT`        | Passport         | No (optional)      |
    | `NATIONAL_ID`     | National ID card | Yes (FRONT + BACK) |
    | `DRIVERS_LICENSE` | Driver's license | Yes (FRONT + BACK) |

    **Address Proof Types:**

    | Type                | Description                                |
    | ------------------- | ------------------------------------------ |
    | `UTILITY_BILL`      | Recent utility bill (gas, electric, water) |
    | `BANK_STATEMENT`    | Bank statement (within last 3 months)      |
    | `GOVERNMENT_LETTER` | Official government correspondence         |
    | `RESIDENCE_PERMIT`  | Residence permit document                  |
    | `PASSPORT`          | Passport showing address                   |
    | `NATIONAL_ID`       | National ID showing address                |
    | `DRIVERS_LICENSE`   | Driver's license showing address           |
    | `COMPANY_DOC`       | Company document showing address           |

    <Tip>
      **Proof of Address Requirements:**

      * Document must show the customer's **full name** and **complete address**
      * Address must match the `address` provided in the customer creation request
      * Document should be issued within the **last 90 days** (for utility bills, bank statements, and government letters)
    </Tip>

    ### Customer Status & Webhooks

    After document submission, customers go through a verification workflow:

    **Status Lifecycle:**

    ```text theme={null}
    INCOMPLETE → REVIEWING → APPROVED
                    ↓
               ON_HOLD / REJECTED
    ```

    | Status       | Description                                     |
    | ------------ | ----------------------------------------------- |
    | `INCOMPLETE` | Customer created but documents not yet attached |
    | `REVIEWING`  | Documents submitted and under compliance review |
    | `APPROVED`   | Verification complete, customer can transact    |
    | `ON_HOLD`    | Additional information or documents required    |
    | `REJECTED`   | Verification failed, see rejection reason       |

    **Webhook Events:**

    * `customer.created` - Fired when customer is created
    * `customer.status` - Fired when status changes

    Subscribe to webhooks to automate your onboarding flow. See [Verifying Webhooks](/guides/webhooks/verifying-webhooks) for setup.

    ### Error Response Examples

    **Email validation error (not lowercase):**

    ```json theme={null}
    {
      "message": "Validation failed",
      "errors": {
        "basic_info.email": ["Email must be all lowercase"]
      }
    }
    ```

    **RELIANCE not enabled:**

    ```json theme={null}
    {
      "message": "RELIANCE is not available for your client"
    }
    ```

    **TIN format validation (USA):**

    ```json theme={null}
    {
      "message": "Validation failed",
      "errors": {
        "basic_info.tin": ["TIN must be in SSN format (xxx-xx-xxxx) for USA customers"]
      }
    }
    ```

    **Missing required field:**

    ```json theme={null}
    {
      "message": "Validation failed",
      "errors": {
        "financial_profile.occupation_id": ["occupation_id is required"]
      }
    }
    ```

    ***

    ## What's Next?

    You've successfully created an individual customer. Here's what to do next:

    ### 1. Monitor Verification Status

    Listen for webhook events to track verification progress:

    * Subscribe to `customer.created` and `customer.status` webhooks
    * Handle status transitions: `INCOMPLETE` → `REVIEWING` → `APPROVED`
    * For `ON_HOLD` statuses, respond to RFIs (Requests for Information) via email or Slack with additional documents
    * See [Webhook Verification](/guides/webhooks/verifying-webhooks) for implementation details

    ### 2. Test Edge Cases

    Validate your integration handles common errors:

    * ✓ Email with uppercase characters
    * ✓ TIN in wrong format for country
    * ✓ Non-Latin characters in text fields
    * ✓ Missing required fields
    * ✓ RELIANCE verification when not enabled
    * ✓ Invalid state codes

    ### 3. Production Checklist

    Before going live, ensure you have:

    * Implemented webhook handling for status updates
    * Added proper error handling for all failure scenarios
    * Client-side validation for email lowercase and TIN format
    * Fetched and cached catalogue data (occupations, purposes, source-of-funds)
    * Implemented document upload UI/flow
    * Set up monitoring for failed verifications
    * Tested the complete workflow end-to-end

    ### 4. Create Beneficiaries

    Once your individual customer is approved, you can create beneficiaries for payouts:

    * See [Beneficiary Account Validation](/api-reference/beneficiaries/account-info-validation)
    * Review [Beneficiary Relationships](/api-reference/beneficiaries/relationships)

    ***

    ## Common Pitfalls & Solutions

    | Pitfall                           | Solution                                                                                                           |
    | --------------------------------- | ------------------------------------------------------------------------------------------------------------------ |
    | **Email validation fails**        | Ensure email is **all lowercase** before sending: `john.doe@example.com` ✓ not `John.Doe@Example.com` ✗            |
    | **RELIANCE 423 error**            | RELIANCE verification must be enabled for your client. Contact support or use `STANDARD` verification type.        |
    | **TIN format rejected**           | TIN must follow the country's official format. For USA, use SSN format `xxx-xx-xxxx`.                              |
    | **Non-Latin character rejection** | All text fields accept only English (Latin) characters. Transliterate or romanize names (e.g., `Jose` not `Jose`). |
    | **State code validation fails**   |                                                                                                                    |
    | **Phone format rejected**         | Use E.164 format with country code: `+14155552671`, not `(415) 555-2671`.                                          |
    | **Monthly volume rejected**       | Provide amount in USD as integer (not cents): `5000` for \$5,000, not `500000`.                                    |
    | **Document side missing**         | For `NATIONAL_ID` and `DRIVERS_LICENSE`, include `side: "FRONT"` and `side: "BACK"` in the files array.            |
    | **Address mismatch**              | Ensure proof of address document shows the same address provided in the `address` object.                          |
  </Tab>
</Tabs>
