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

# Update Cardholder

> Update cardholder personal information, metadata, or status. PATCH /cardholders/{id}.

## Overview

Update cardholder information. Only the fields you provide will be updated. Note that the email address cannot be changed after creation.

## Path Parameters

| Parameter | Type   | Description                  |
| --------- | ------ | ---------------------------- |
| `id`      | string | Unique cardholder identifier |

## Updatable Fields

| Field            | Type   | Description                                                 |
| ---------------- | ------ | ----------------------------------------------------------- |
| `firstName`      | string | First name                                                  |
| `lastName`       | string | Last name                                                   |
| `phone`          | string | Phone number in E.164 format                                |
| `dateOfBirth`    | string | Date of birth (`YYYY-MM-DD`, must be 18+)                   |
| `gender`         | string | Gender (`MALE` or `FEMALE`)                                 |
| `address`        | string | Street address                                              |
| `city`           | string | City                                                        |
| `state`          | string | State or province                                           |
| `country`        | string | ISO country code (2 chars)                                  |
| `zipCode`        | string | Postal/ZIP code                                             |
| `documentType`   | string | Document type (`PASSPORT`, `NATIONAL_ID`, `DRIVER_LICENSE`) |
| `documentNumber` | string | Document number                                             |
| `externalId`     | string | Your system's identifier                                    |
| `status`         | string | Status (`ACTIVE`, `INACTIVE`, `SUSPENDED`)                  |
| `metadata`       | object | Custom key-value data (merge semantics, see below)          |

## Metadata (Merge Semantics)

The `metadata` field uses **merge semantics** on update:

* **Add a key**: include the key with a value
* **Update a key**: include the key with a new value
* **Delete a key**: set the key to `null` or `""`
* Keys you don't include are left unchanged

```json theme={null}
// Existing metadata: { "department": "Engineering", "tier": "VIP" }

// This request:
{ "metadata": { "tier": "Premium", "cost_center": "CC-500", "department": "" } }

// Results in: { "tier": "Premium", "cost_center": "CC-500" }
// "tier" was updated, "cost_center" was added, "department" was deleted
```

<Tip>
  To clear all metadata, pass an empty object with every key set to `null`.
</Tip>

## Example Usage

<CodeGroup>
  ```php PHP theme={null}
  <?php
  $cardholderId = 'CH1a2b3c4d5e6f';

  $data = [
      'phone' => '+1987654321',
      'address' => '456 Oak Avenue',
      'city' => 'Los Angeles',
      'state' => 'CA',
      'metadata' => [
          'department' => 'Sales',        // update existing key
          'badge_number' => 'B-789',      // add new key
      ],
  ];

  $response = file_get_contents(
      "https://api.fyatu.com/api/v3/cardholders/{$cardholderId}",
      false,
      stream_context_create([
          'http' => [
              'method' => 'PATCH',
              'header' => [
                  'Authorization: Bearer ' . $accessToken,
                  'Content-Type: application/json'
              ],
              'content' => json_encode($data)
          ]
      ])
  );

  $result = json_decode($response, true);
  echo "Updated cardholder: " . $result['data']['id'] . "\n";
  ```

  ```javascript Node.js theme={null}
  const cardholderId = 'CH1a2b3c4d5e6f';

  const data = {
    phone: '+1987654321',
    address: '456 Oak Avenue',
    city: 'Los Angeles',
    state: 'CA',
    metadata: {
      department: 'Sales',        // update existing key
      badge_number: 'B-789',      // add new key
    },
  };

  const response = await fetch(
    `https://api.fyatu.com/api/v3/cardholders/${cardholderId}`,
    {
      method: 'PATCH',
      headers: {
        'Authorization': `Bearer ${accessToken}`,
        'Content-Type': 'application/json'
      },
      body: JSON.stringify(data)
    }
  );

  const result = await response.json();
  console.log('Updated cardholder:', result.data.id);
  ```
</CodeGroup>

## Example Response

The response returns the complete updated cardholder data:

```json theme={null}
{
  "success": true,
  "status": 200,
  "message": "Cardholder updated successfully",
  "data": {
    "id": "ch_a1b2c3d4e5f6",
    "externalId": "EXT-0001",
    "firstName": "Alice",
    "lastName": "Example",
    "email": "alice@example.com",
    "phone": "+15550009876",
    "dateOfBirth": "1990-01-01",
    "gender": "FEMALE",
    "address": {
      "line1": "456 Oak Avenue",
      "city": "Los Angeles",
      "state": "CA",
      "country": "US",
      "zipCode": "90001"
    },
    "document": {
      "type": "PASSPORT",
      "number": "AB1234567"
    },
    "kyc": {
      "status": "UNSUBMITTED",
      "idFrontUrl": null,
      "idBackUrl": null,
      "selfieUrl": null
    },
    "status": "ACTIVE",
    "metadata": {
      "department": "Sales",
      "badge_number": "B-789"
    },
    "createdAt": "2026-01-15 21:31:39",
    "updatedAt": "2026-01-16T00:37:34+00:00"
  },
  "meta": {
    "requestId": "req_7d30cd59796bbcf0e903b5fd",
    "timestamp": "2026-01-16T00:37:34+00:00"
  }
}
```

## Suspend/Reactivate Cardholder

You can change the cardholder's status to temporarily suspend or reactivate them:

```json theme={null}
// Suspend a cardholder
{ "status": "SUSPENDED" }

// Reactivate a cardholder
{ "status": "ACTIVE" }

// Mark as inactive
{ "status": "INACTIVE" }
```

<Warning>
  Suspending a cardholder does not automatically suspend their cards. You should manage card statuses separately if needed.
</Warning>

<Note>
  The `email` field cannot be updated after cardholder creation. If you need to change the email, you must delete the cardholder and create a new one.
</Note>

<Note>
  The `documentType` and `documentNumber` fields are locked once the cardholder's KYC status is `ACCEPTED` or `SUBMITTED`. You cannot modify document information after KYC verification.
</Note>


## OpenAPI

````yaml v3/openapi.json PATCH /cardholders/{id}
openapi: 3.1.0
info:
  title: FYATU API v3
  description: >-
    FYATU API v3 with JWT authentication for Collections, Payouts, and Card
    Issuing.
  version: 3.0.0
  contact:
    name: FYATU Support
    url: https://fyatu.com
    email: support@fyatu.com
servers:
  - url: https://api.fyatu.com/api/v3
    description: Production
security: []
tags:
  - name: Authentication
    description: JWT token management endpoints
  - name: Account
    description: Business account, wallet, and address management
  - name: Collections
    description: Accept payments from customers via checkout sessions
  - name: Refunds
    description: Issue refunds for completed collections
  - name: Payouts
    description: Send money to Fyatu account holders
  - name: Cardholders
    description: Cardholder management for card issuing programs
  - name: Cards
    description: Issue, fund, freeze, and manage virtual cards
  - name: Webhooks
    description: Webhook configuration and management
paths:
  /cardholders/{id}:
    patch:
      tags:
        - Cardholders
      summary: Update Cardholder
      description: >-
        Update cardholder information. Only provided fields will be updated.
        Email cannot be changed after creation.
      operationId: updateCardholder
      parameters:
        - name: id
          in: path
          required: true
          schema:
            type: string
          description: Unique cardholder identifier
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/CardholderUpdateRequest'
            example:
              phone: '+1987654321'
              address: 456 Oak Avenue
              city: Los Angeles
              state: CA
      responses:
        '200':
          description: Cardholder updated successfully
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/CardholderResponse'
              example:
                success: true
                status: 200
                message: Cardholder updated successfully
                data:
                  id: ch_a1b2c3d4e5f6
                  externalId: EXT-0001
                  firstName: Alice
                  lastName: Example
                  email: alice@example.com
                  phone: '+15550009876'
                  dateOfBirth: '1990-01-01'
                  gender: FEMALE
                  address:
                    line1: 456 Example Avenue
                    city: Los Angeles
                    state: CA
                    country: US
                    zipCode: '90001'
                  document:
                    type: PASSPORT
                    number: XX0000000
                  kyc:
                    status: ACCEPTED
                    idFrontUrl: null
                    idBackUrl: null
                    selfieUrl: null
                  metadata: null
                  status: ACTIVE
                  cardsCount: 1
                  createdAt: '2026-01-10T14:30:00Z'
                  updatedAt: '2026-01-17T11:00:00Z'
                meta:
                  requestId: req_e5f6g7h8i9j0
                  timestamp: '2026-01-17T11:00:00Z'
        '400':
          $ref: '#/components/responses/ValidationError'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '404':
          $ref: '#/components/responses/NotFound'
        '409':
          description: Conflict - externalId already in use
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
      security:
        - BearerAuth: []
components:
  schemas:
    CardholderUpdateRequest:
      type: object
      properties:
        firstName:
          type: string
          minLength: 1
          maxLength: 100
          description: Cardholder's first name
        lastName:
          type: string
          minLength: 1
          maxLength: 100
          description: Cardholder's last name
        phone:
          type: string
          minLength: 6
          maxLength: 20
          description: Phone number with country code
        dateOfBirth:
          type: string
          format: date
          description: Date of birth (YYYY-MM-DD)
        gender:
          type: string
          enum:
            - MALE
            - FEMALE
            - OTHER
          description: Gender
        address:
          type: string
          maxLength: 255
          description: Street address
        city:
          type: string
          maxLength: 100
          description: City
        state:
          type: string
          maxLength: 100
          description: State or province
        country:
          type: string
          minLength: 2
          maxLength: 2
          description: ISO 3166-1 alpha-2 country code
        zipCode:
          type: string
          maxLength: 20
          description: Postal/ZIP code
        documentType:
          type: string
          enum:
            - PASSPORT
            - NATIONAL_ID
            - DRIVER_LICENSE
          description: Type of identification document
        documentNumber:
          type: string
          maxLength: 50
          description: Document identification number
        externalId:
          type: string
          maxLength: 100
          description: Your system's identifier
        status:
          type: string
          enum:
            - ACTIVE
            - INACTIVE
            - SUSPENDED
          description: Cardholder status
    CardholderResponse:
      type: object
      description: Response for create and update cardholder operations
      properties:
        success:
          type: boolean
          example: true
        status:
          type: integer
          example: 201
        message:
          type: string
        data:
          type: object
          properties:
            id:
              type: string
              example: ch_1a2b3c4d5e6f7890abcdef1234567890
            externalId:
              type: string
              nullable: true
            firstName:
              type: string
            lastName:
              type: string
            email:
              type: string
            phone:
              type: string
            dateOfBirth:
              type: string
              format: date
            gender:
              type: string
              enum:
                - MALE
                - FEMALE
                - OTHER
              nullable: true
            address:
              type: object
              properties:
                line1:
                  type: string
                  nullable: true
                city:
                  type: string
                  nullable: true
                state:
                  type: string
                  nullable: true
                country:
                  type: string
                zipCode:
                  type: string
                  nullable: true
            document:
              type: object
              description: Document info (included in update response)
              properties:
                type:
                  type: string
                  enum:
                    - PASSPORT
                    - NATIONAL_ID
                    - DRIVER_LICENSE
                  nullable: true
                number:
                  type: string
                  nullable: true
            kyc:
              type: object
              description: KYC info (included in update response)
              properties:
                status:
                  type: string
                  enum:
                    - UNSUBMITTED
                    - SUBMITTED
                    - ACCEPTED
                    - REJECTED
                idFrontUrl:
                  type: string
                  nullable: true
                idBackUrl:
                  type: string
                  nullable: true
                selfieUrl:
                  type: string
                  nullable: true
            status:
              type: string
              enum:
                - ACTIVE
                - INACTIVE
                - SUSPENDED
            kycStatus:
              type: string
              enum:
                - UNSUBMITTED
                - SUBMITTED
                - ACCEPTED
                - REJECTED
              description: 'Deprecated: use kyc.status instead'
            createdAt:
              type: string
              format: date-time
            updatedAt:
              type: string
              format: date-time
              nullable: true
        meta:
          $ref: '#/components/schemas/Meta'
    ErrorResponse:
      type: object
      properties:
        success:
          type: boolean
          example: false
        status:
          type: integer
          example: 401
        message:
          type: string
          example: Invalid credentials
        error:
          $ref: '#/components/schemas/Error'
        meta:
          $ref: '#/components/schemas/Meta'
    Meta:
      type: object
      properties:
        requestId:
          type: string
          description: Unique request ID for tracking
          example: req_abc123def456
        timestamp:
          type: string
          format: date-time
          description: ISO 8601 timestamp of the response
    Error:
      type: object
      properties:
        code:
          type: string
          description: Error code for programmatic handling
          example: AUTH_INVALID_CREDENTIALS
        details:
          type: array
          items:
            $ref: '#/components/schemas/ValidationError'
          description: Validation error details (for VALIDATION_ERROR)
    ValidationError:
      type: object
      properties:
        field:
          type: string
          description: Field that failed validation
          example: appId
        message:
          type: string
          description: Validation error message
          example: AppId is required
  responses:
    ValidationError:
      description: Validation failed
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
          example:
            success: false
            status: 400
            message: Validation failed
            error:
              code: VALIDATION_ERROR
              details:
                - field: currency
                  message: Currency is required
            meta:
              requestId: req_abc123
              timestamp: '2026-01-05T10:30:00+00:00'
    Unauthorized:
      description: Authentication required or token invalid
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
          example:
            success: false
            status: 401
            message: Unable to identify business
            error:
              code: AUTH_TOKEN_INVALID
            meta:
              requestId: req_abc123
              timestamp: '2026-01-05T10:30:00+00:00'
    NotFound:
      description: Resource not found
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
          example:
            success: false
            status: 404
            message: Wallet not found
            error:
              code: RESOURCE_NOT_FOUND
            meta:
              requestId: req_abc123
              timestamp: '2026-01-05T10:30:00+00:00'
  securitySchemes:
    BearerAuth:
      type: http
      scheme: bearer
      bearerFormat: JWT
      description: JWT access token obtained from /auth/token

````