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

# Upgrade Guide

> This guide covers breaking changes across Platform API versions and how to upgrade.

The Platform API uses dated versions. Set the version on each request with the `Accept-Version` header. For support timelines, see [API Versioning](./versioning).

## Available versions

| Version | Accept-Version header | Description |
| :- | :- | :- |
| **v20260929** | `v20260929` | Current release. Consolidated response schemas, updated aggregation behavior, sunset managed endpoints. |
| **v20250224** | `v20250224` | Enhanced search and filtering with product support. New `data_request` field for product-based aggregation. |
| **v20111101** | `v20111101` | Legacy version. Not recommended for new implementations. |

If you are on v20111101, complete [Upgrading from v20111101 to v20250224](#upgrading-from-v20111101-to-v20250224) first, then continue with [Upgrading from v20250224 to v20260929](#upgrading-from-v20250224-to-v20260929).

## Upgrading from v20250224 to v20260929

### Key changes in v20260929

v20260929 redesigns how the Platform API structures responses for key resources, adds new capabilities for merchant intelligence, and enables secure data sharing. Key changes include:

* **Data minimization:** Responses for members, accounts, transactions, rewards, statements, account owners, account numbers, member status, and institutions are slimmer by default. The new [Layered Responses](#layered-responses) structure returns core fields by default, related objects on full resource requests, and extra data only when you opt in.
* **Enhanced merchant coverage:** The `merchant` Include returns a `confidence_level` field indicating match quality (for example, "Very High" or "Low"). The new `counterparties` Include returns every party involved in a transaction, unlike `merchant`, which returns only the primary merchant. Each counterparty includes `guid`, `name`, `confidence_level`, `logo_url`, `website_url`, and `self`. For example, ordering McDonald's through DoorDash:

  * `merchant` = DoorDash (the payment processor)
  * `counterparties` = \[DoorDash, McDonald's] (all involved parties)
* **Built-in navigation with the `self` field:** Overhauled resources include a `self` URI to their detail endpoint. Follow `self` links from list responses instead of constructing URIs manually.
* **Data Exchange:** New endpoints support client-to-client financial data sharing. Issuers grant access to grantees via client grants; grantees exchange grants for tokens and call namespaced Data Exchange endpoints. See [Data Exchange](/api-reference/platform-api/v20260929/reference/data-exchange) for the full workflow and endpoint reference.

### Breaking changes in v20260929

The following changes require updates to your integration. Each links to the upgrade step with the details.

| Area | Breaking change | Upgrade step |
| - | - | - |
| Version header | Set `Accept-Version` to `v20260929` on all requests. | [Update your version header](#version-header) |
| Response structure | Responses for members, accounts, transactions, rewards, statements, account owners, account numbers, member status, and institutions return fewer top-level fields. Identifiers move into Companion objects (for example, `user_guid` is now `user.guid`). | [Update response parsing](#layered-responses) |
| Resource fields | Many fields are renamed, relocated, restructured, or removed on each overhauled resource. On institutions, `supported_products` is now `products`, in both the response and the List Institutions filter. | [Update response parsing](#layered-responses) |
| Member status | The response envelope key changes from `member` to `member_status`, and several fields are renamed or removed. | [Update response parsing](#layered-responses) |
| `includes` parameter | Changes from a comma-separated string to `includes[]` array syntax. `merchants` and `repeating_transactions` are renamed; `geolocations` and `classifications` are removed. | [Update the includes query parameter](#includes-query-parameter) |
| Member create body | `data_request` is required. OAuth fields move into a new `oauth` object. `skip_aggregation` is removed. | [Update the member create request body](#member-create-request-body) |
| OAuth authorization URL | `GET .../oauth_window_uri` is replaced by `POST .../oauth/authorization_url`, which requires `data_request`. The response envelope key changes from `member` to `oauth`. | [Replace the OAuth authorization URL endpoint](#oauth-authorization-url-endpoint) |
| Request Widget URL | `data_request` can't be combined with `mode`, `include_transactions`, or `include_identity`. `ui_message_version` is no longer supported. | [Update Request Widget URL requests](#widget-url-requests) |
| Aggregation endpoints | Endpoints are renamed to match product names and now return the `member_status` response. The old paths are deprecated. | [Update aggregation endpoints](#aggregation-endpoints) |
| Date filters | Transaction date filters use ISO 8601 date strings (`YYYY-MM-DD`) instead of Unix timestamps. | [Revert date filters to ISO 8601](#date-filters) |
| Managed data endpoints | Managed institution and managed member endpoints are sunset and return `410 Gone`. | [Stop using sunset and deprecated endpoints](#deprecated-and-sunset-endpoints) |

### Upgrade steps for v20260929

Complete these steps to move your integration from v20250224 to v20260929.

<Steps titleSize="h4">
  <Step title="Update your version header" id="version-header">
    Change `Accept-Version` to `v20260929` on all requests.
  </Step>

  <Step title="Update response parsing" id="layered-responses">
    Layered Responses is the core of the v20260929 redesign. Responses for members, accounts, transactions, rewards, statements, account owners, account numbers, member status, and institutions now return fewer top-level fields. Related resource data has moved into related objects called **Companions**. For example, `user_guid` is now `user.guid`.

    Start with the structure, then update each resource you use. Responses now use a **Layered Responses** structure, split into three tiers: the **Base** (core fields returned by default), **Companions** (related objects returned alongside a full resource request), and **Includes** (opt-in fields returned only when you ask for them with `includes[]`).

    <AccordionGroup>
      <Accordion title="Layer 1: Base Response">
        Every resource has a core set of fields that comprise the **Base** response (the fields returned by default). Any response that returns or references the resource includes these fields.

        **Base characteristics:**

        * Contains MX and partner identifiers for the resource.
        * Resource-specific attributes such as the balance for an Account or the amount for a Transaction.
        * A `self` link (URI) to the resource's Read endpoint. Follow it instead of constructing URIs manually.

        When a resource appears as a Companion (a related object nested inside another resource), it uses this same Base shape. A member's Base on an account response is structurally identical to a member's Base when fetched directly.
      </Accordion>

      <Accordion title="Layer 2: Full Resource Response (Base + Companions)">
        When you request a resource directly (for example, `GET /users/{user_guid}/members/{member_guid}`), you receive the Base and all **Companions** — related objects such as the `member` and `user` on an Account response.

        **Companion characteristics:**

        * Always present (not opt-in) on full resource endpoints.
        * Always in Base form (never nested more than one level deep).
        * Resources persisted by MX contain an `mx_record`.

        **`mx_record`**: Contains `created_at` and `updated_at` timestamps (UTC, ISO 8601). Present on all resources that correspond to persisted records, absent on representational sub-resources like `member_status`.

        * These timestamps reflect when the record was created or last modified on the MX platform, not when the underlying resource was created. For example, `account.mx_record.created_at` is when the account was first recorded on the platform, not when it was opened at the institution.

        **Read Member response** (GET `/users/{user_guid}/members/{member_guid}`):

        `guid`, `id`, `metadata`, `name`, and `self` are the member's **Base fields**. The remaining keys (`institution`, `user`, `member_status`, `oauth`, `mx_record`) are the **Companions**.

        ```json theme={null}
        {
          "member": {
            "guid": "MBR-7c6f361b-e582-15b6-60c0-358f12466b4b",
            "id": "member-1234",
            "metadata": "\"credentials_last_refreshed_at\": \"2015-10-15\"",
            "name": "MX Bank",
            "self": "/users/USR-.../members/MBR-...",
            "institution": {
              "code": "mx_bank",
              "guid": "INS-123",
              "name": "MX Bank",
              "self": "/institutions/INS-123"
            },
            "user": {
              "guid": "USR-11141024-90b3-1bce-cac9-c06ced52ab4c",
              "id": "U-201709221210",
              "self": "/users/USR-..."
            },
            "member_status": {
              "status": "CHALLENGED",
              "error": { "error_type": "AUTHENTICATION", "..." : "..." },
              "self": "/users/USR-.../members/MBR-.../status"
            },
            "oauth": {
              "is_oauth": true,
              "authorization_url": "https://mxbank.mx.com/oauth/authorize?...",
              "self": "/users/USR-.../members/MBR-.../oauth/authorization_url"
            },
            "mx_record": {
              "created_at": "2024-03-15T10:30:00.000Z",
              "updated_at": "2025-06-01T14:22:00.000Z"
            }
          }
        }
        ```
      </Accordion>

      <Accordion title="Layer 3: Includes (Opt-In Data)">
        Additional response data — called **Includes** because you opt in to them with the `includes[]` query parameter — is available on select endpoints.

        **List Transactions example**

        ```text theme={null}
        GET /users/{user_guid}/accounts/{account_guid}/transactions?includes[]=merchant&includes[]=counterparties
        ```

        <Note>
          Includes keys are absent from the response entirely unless requested. When requested but no data exists, the value is `null`. See the individual endpoint documentation for more information.
        </Note>
      </Accordion>

      <Accordion title="Identifier relocation">
        Resource identifiers moved from top-level fields into their Companion (related) objects. For example, `user_guid` and `institution_code` are now `user.guid` and `institution.code`.

        <CodeGroup>
          ```json After (v20260929) theme={null}
          {
            "member": {
              "guid": "MBR-...",
              "user": {
                "guid": "USR-123",
                "self": "/users/USR-123"
              },
              "institution": {
                "code": "mxbank",
                "guid": "INS-123",
                "self": "/institutions/INS-123"
              }
            }
          }
          ```

          ```json Before (v20250224) theme={null}
          {
            "member": {
              "guid": "MBR-...",
              "user_guid": "USR-123",
              "institution_code": "mxbank"
            }
          }
          ```
        </CodeGroup>
      </Accordion>
    </AccordionGroup>

    Then apply the field-level changes for each resource you use. Expand a resource to see its changes.

    <AccordionGroup>
      <Accordion title="Account">
        Reduced from \~60 fields to 8 base fields + companions. See [Accounts endpoint documentation](/api-reference/platform-api/v20260929/reference/accounts) for the full response schema.

        | Change type | Field |
        | - | - |
        | **Renamed** | `account_number` → `account_number_display` |
        | **Relocated** | `user_guid` → `user.guid` |
        | | `user_id` → `user.id` |
        | | `member_guid` → `member.guid` |
        | | `member_id` → `member.id` |
        | | `created_at` → `mx_record.created_at` |
        | | `updated_at` → `mx_record.updated_at` |
        | **Removed** | `account_ownership`, `annuity_policy_to_date`, `annuity_provider`, `annuity_term_year`, `apr`, `apy`, `available_balance`, `available_credit`, `balance`, `cash_balance`, `cash_surrender_value`, `credit_limit`, `currency_code`, `day_payment_is_due`, `death_benefit`, `federal_insurance_status`, `imported_at`, `interest_rate`, `institution_code`, `insured_name`, `is_closed`, `is_hidden`, `is_manual`, `last_payment`, `last_payment_at`, `loan_amount`, `margin_balance`, `matures_on`, `member_is_managed_by_user`, `metadata`, `minimum_balance`, `minimum_payment`, `original_balance`, `pay_out_amount`, `payment_due_at`, `payoff_balance`, `premium_amount`, `property_type`, `routing_number`, `started_on`, `statement_balance`, `today_ugl_amount`, `today_ugl_percentage`, `total_account_value`, `total_account_value_ugl` |
        | **Added** | `self`, `member` companion, `user` companion, `mx_record` companion |
      </Accordion>

      <Accordion title="Account number">
        Account number fields are now nested objects grouped by payment network. `ach` and `eft` are nullable and populated only when applicable. See [Account Numbers endpoint documentation](/api-reference/platform-api/v20260929/reference/accounts#account-number-fields) for the full response schema.

        | Change type | Field |
        | - | - |
        | **Restructured** | `account_number`, `routing_number` → `ach.account_number`, `ach.routing_number` |
        | | `institution_number`, `transit_number` → `eft.institution_number`, `eft.transit_number` |
        | **Relocated** | `account_guid` → `account.guid` |
        | | `member_guid` → `member.guid` |
        | | `user_guid` → `user.guid` |
        | **Removed** | `loan_guarantor`, `loan_reference_number`, `passed_validation`, `sequence_number` |
        | **Added** | `account` companion, `member` companion, `user` companion, `mx_record` companion |

        ```json theme={null}
        {
          "account_number": {
            "guid": "ACN-...",
            "ach": { "account_number": "3331261", "routing_number": "68899990000000" },
            "eft": null,
            "account": { "guid": "ACT-...", "name": "...", "self": "..." },
            "member": { "guid": "MBR-...", "name": "...", "self": "..." },
            "user": { "guid": "USR-...", "id": "U-123", "self": "/users/USR-..." }
          }
        }
        ```
      </Accordion>

      <Accordion title="Account owner">
        Account owner fields are now arrays, allowing multiple names, addresses, phone numbers, and emails per owner. See [Account Owners endpoint documentation](/api-reference/platform-api/v20260929/reference/accounts#account-owner-fields) for the full response schema.

        | Change type | Field |
        | - | - |
        | **Restructured** | `owner_name`, `first_name`, `last_name` → `names[]` array of `{ name, first_name, last_name }` |
        | | `address`, `city`, `state`, `postal_code`, `country` → `addresses[]` array of `{ street, city, state, postal_code, country }` |
        | | `phone` → `phone_numbers[]` array of `{ phone }` |
        | | `email` → `emails[]` array of `{ email }` |
        | **Relocated** | `account_guid` → `account.guid` |
        | | `member_guid` → `member.guid` |
        | | `user_guid` → `user.guid` |
        | **Added** | `account` companion, `member` companion, `user` companion, `mx_record` companion |

        ```json theme={null}
        {
          "account_owner": {
            "guid": "ACO-...",
            "names": [{ "name": "Josh Smith", "first_name": "Josh", "last_name": "Smith" }],
            "addresses": [{ "street": "3541 Adrian Street", "city": "Middlesex", "state": "VA", "postal_code": "00000-0000", "country": "US" }],
            "phone_numbers": [{ "phone": "555-555-5555" }],
            "emails": [{ "email": "example@example.com" }],
            "account": { "guid": "ACT-...", "name": "...", "self": "..." },
            "member": { "guid": "MBR-...", "name": "...", "self": "..." },
            "user": { "guid": "USR-...", "id": "U-123", "self": "/users/USR-..." }
          }
        }
        ```
      </Accordion>

      <Accordion title="Institution">
        Reduced from 20 fields to 6 base fields + `mx_record`. The `supported_products` array is renamed to `products`, and the List Institutions filter changes from `supported_products[]` to `products[]`. See [List Institutions endpoint documentation](/api-reference/platform-api/v20260929/reference/institutions/list-institutions) for the full response schema.

        | Change type | Field |
        | - | - |
        | **Renamed** | `supported_products` → `products` |
        | | `supported_products[]` query parameter → `products[]` (List Institutions) |
        | **Relocated** | `created_at` → `mx_record.created_at` |
        | **Removed** | `client_status`, `forgot_password_url`, `forgot_username_url`, `instructional_text`, `instructional_text_steps`, `is_disabled_by_client`, `is_hidden`, `medium_logo_url`, `small_logo_url`, `status`, `supports_oauth`, `supports_tax_document`, `trouble_signing_in_url`, `url` |
        | **Added** | `self`, `mx_record` companion |

        ```json theme={null}
        {
          "institution": {
            "code": "mxbank",
            "guid": "INS-1572a04c-912b-59bf-5841-332c7dfafaef",
            "iso_country_code": "US",
            "name": "MX Bank",
            "products": ["account_verification", "identity_verification", "transactions", "transaction_history"],
            "self": "/institutions/INS-1572a04c-912b-59bf-5841-332c7dfafaef",
            "mx_record": {
              "created_at": "2024-03-15T10:30:00.000Z",
              "updated_at": "2025-06-01T14:22:00.000Z"
            }
          }
        }
        ```
      </Accordion>

      <Accordion title="Member">
        Reduced from \~25 fields to 5 base fields + companions. See [Members endpoint documentation](/api-reference/platform-api/v20260929/reference/members) for the full response schema.

        | Change type | Field |
        | - | - |
        | **Relocated** | `user_guid` → `user.guid` |
        | | `user_id` → `user.id` |
        | | `institution_code` → `institution.code` |
        | | `institution_guid` → `institution.guid` |
        | | `connection_status` → `member_status.status` |
        | | `error` → `member_status.error` |
        | | `is_oauth` → `oauth.is_oauth` |
        | | `oauth_window_uri` → `oauth.authorization_url` |
        | **Removed** | `aggregated_at`, `background_aggregation_is_disabled`, `connection_status_message`, `is_being_aggregated`, `is_managed_by_user`, `is_manual`, `most_recent_job_detail_code`, `most_recent_job_detail_text`, `most_recent_job_guid`, `needs_updated_credentials`, `successfully_aggregated_at`, `use_cases` |
        | **Added** | `self`, `institution` companion, `member_status` companion, `oauth` companion, `user` companion, `mx_record` companion |
      </Accordion>

      <Accordion title="Member status">
        The response envelope key changes from `member` to `member_status`, and a new `products` Companion provides per-product support status. Aggregation endpoints now return this response. See [Read Member Status endpoint documentation](/api-reference/platform-api/v20260929/reference/members/read-member-status) for the full response schema.

        | v20250224 field | v20260929 equivalent |
        | - | - |
        | Response key: `member` | Response key: `member_status` |
        | `connection_status` | `status` (base) |
        | `aggregated_at` | `products.last_attempted_at` |
        | `successfully_aggregated_at` | `products.last_updated_at` |
        | `guid` | `member.guid` (companion) |
        | `has_processed_accounts` | Removed |
        | `has_processed_transactions` | Removed |
        | `has_processed_account_numbers` | Removed |
        | `is_authenticated` | Removed |
        | `is_being_aggregated` | Removed |
        | -- | `error` (new) |
        | -- | `self` (new) |
        | -- | `user` companion (new) |

        ```json theme={null}
        {
          "member_status": {
            "status": "CONNECTED",
            "error": null,
            "self": "/users/USR-.../members/MBR-.../status",
            "challenges": [],
            "member": { "guid": "MBR-...", "id": null, "name": "MX Bank", "self": "..." },
            "products": {
              "last_attempted_at": "2025-01-13T17:57:38Z",
              "last_updated_at": "2025-01-13T17:57:38Z",
              "account_verification": { "is_supported": true },
              "identity_verification": { "is_supported": true },
              "transactions": { "is_supported": true },
              "transaction_history": { "is_supported": true },
              "statements": { "is_supported": true },
              "investments": { "is_supported": false },
              "rewards": { "is_supported": false }
            },
            "user": { "guid": "USR-...", "id": "U-123", "self": "/users/USR-..." }
          }
        }
        ```
      </Accordion>

      <Accordion title="Rewards">
        Reduced from \~10 fields to 5 base fields + companions. See [Rewards endpoint documentation](/api-reference/platform-api/v20260929/reference/rewards/list-rewards) for the full response schema.

        | Change type | Field |
        | - | - |
        | **Relocated** | `account_guid` → `account.guid` |
        | | `member_guid` → `member.guid` |
        | | `user_guid` → `user.guid` |
        | | `created_at` → `mx_record.created_at` |
        | | `updated_at` → `mx_record.updated_at` |
        | **Removed** | `balance_type`, `expires_on` |
        | **Added** | `self`, `account` companion, `member` companion, `user` companion, `mx_record` companion |
      </Accordion>

      <Accordion title="Statements">
        Reduced from \~8 fields to 3 base fields + companions. See [Statements endpoint documentation](/api-reference/platform-api/v20260929/reference/statements) for the full response schema.

        | Change type | Field |
        | - | - |
        | **Relocated** | `account_guid` → `account.guid` |
        | | `member_guid` → `member.guid` |
        | | `user_guid` → `user.guid` |
        | | `created_at` → `mx_record.created_at` |
        | | `updated_at` → `mx_record.updated_at` |
        | **Added** | `account` companion, `member` companion, `user` companion, `mx_record` companion |
      </Accordion>

      <Accordion title="Transactions">
        Reduced from \~40 fields to 9 base fields + companions. List and Read Transaction endpoints also support opt-in `includes[]`. Create Transaction does not. See [Transactions endpoint documentation](/api-reference/platform-api/v20260929/reference/transactions) for the full response schema.

        | Change type | Field |
        | - | - |
        | **Relocated** | `account_guid` → `account.guid` |
        | | `account_id` → `account.id` |
        | | `member_guid` → `member.guid` |
        | | `user_guid` → `user.guid` |
        | | `user_id` → `user.id` |
        | | `category` → `category.name` (include) |
        | | `category_guid` → `category.guid` (include) |
        | | `merchant_guid` → `merchant.guid` (include) |
        | | `created_at` → `mx_record.created_at` |
        | | `updated_at` → `mx_record.updated_at` |
        | **Removed** | `check_number_string`, `extended_transaction_type`, `is_bill_pay`, `is_direct_deposit`, `is_expense`, `is_fee`, `is_income`, `is_international`, `is_manual`, `is_overdraft_fee`, `is_payroll_advance`, `is_recurring`, `is_subscription`, `latitude`, `localized_description`, `localized_memo`, `longitude`, `member_is_managed_by_user`, `memo`, `merchant_category_code`, `merchant_location_guid`, `metadata`, `original_description`, `posted_at`, `top_level_category`, `transacted_at` |
        | **Added** | `self`, `account` companion, `member` companion, `user` companion, `mx_record` companion |

        See [Update the includes query parameter](#includes-query-parameter) for changes to the `includes[]` query parameter on List/Read Transaction endpoints.
      </Accordion>
    </AccordionGroup>
  </Step>

  <Step title="Update the includes query parameter" id="includes-query-parameter">
    The `includes` query parameter changes from a comma-separated string to an array format, and the set of accepted values has changed. New supported values are `merchant`, `counterparties`, `category`, and `repeating_transaction`.

    <CodeGroup>
      ```text After (v20260929) theme={null}
      GET /users/{user_guid}/transactions?includes[]=merchant&includes[]=counterparties
      ```

      ```text Before (v20250224) theme={null}
      GET /users/{user_guid}/transactions?includes=merchants,geolocations
      ```
    </CodeGroup>

    | v20250224 value | v20260929 equivalent |
    | - | - |
    | `merchants` | `merchant` |
    | `repeating_transactions` | `repeating_transaction` |
    | `geolocations` | Removed |
    | `classifications` | Removed |
    | -- | `category` (new) |
    | -- | `counterparties` (new) |
  </Step>

  <Step title="Update the member create request body" id="member-create-request-body">
    `data_request` is now required. OAuth-related fields move from the top level into a new `oauth` object. The `skip_aggregation` field, deprecated in v20250224, is removed; use `data_request.products` to control which products aggregate on member creation.

    <CodeGroup>
      ```json After (v20260929) theme={null}
      {
        "member": {
          "institution_code": "mxbank",
          "credentials": [
            { "guid": "CRD-1234", "value": "username" },
            { "guid": "CRD-5678", "value": "password" }
          ]
        },
        "oauth": {
          "client_redirect_url": "https://example.com/callback",
          "enable_app2app": true,
          "referral_source": "APP",
          "ui_message_webview_url_scheme": "mx"
        },
        "data_request": {
          "products": ["transactions", "identity_verification"]
        }
      }
      ```

      ```json Before (v20250224) theme={null}
      {
        "client_redirect_url": "https://example.com/callback",
        "enable_app2app": true,
        "referral_source": "APP",
        "ui_message_webview_url_scheme": "mx",
        "member": {
          "institution_code": "mxbank",
          "credentials": [
            { "guid": "CRD-1234", "value": "username" },
            { "guid": "CRD-5678", "value": "password" }
          ],
          "skip_aggregation": false
        },
        "data_request": {
          "products": ["transactions", "identity_verification"]
        }
      }
      ```
    </CodeGroup>

    | Change | Detail |
    | :- | :- |
    | `client_redirect_url` | Moved to `oauth.client_redirect_url` |
    | `enable_app2app` | Moved to `oauth.enable_app2app` |
    | `referral_source` | Moved to `oauth.referral_source` |
    | `ui_message_webview_url_scheme` | Moved to `oauth.ui_message_webview_url_scheme` |
    | `skip_aggregation` | Removed. Use `data_request.products` |
    | `data_request` | Now required |

    Apart from removing `skip_aggregation`, the `member` and `data_request` objects are unchanged. See the [Create Member endpoint documentation](/api-reference/platform-api/v20260929/reference/members/create-member) for the full request schema.
  </Step>

  <Step title="Replace the OAuth authorization URL endpoint" id="oauth-authorization-url-endpoint">
    The OAuth authorization URL endpoint changes from a `GET` with query parameters to a `POST` with a request body that mirrors the member create body.

    <CodeGroup>
      ```text After (v20260929) theme={null}
      POST /users/{user_guid}/members/{member_guid}/oauth/authorization_url

      {
        "oauth": {
          "client_redirect_url": "https://example.com/callback",
          "enable_app2app": true,
          "referral_source": "APP",
          "ui_message_webview_url_scheme": "mx"
        },
        "data_request": {
          "products": ["transactions", "identity_verification"]
        }
      }
      ```

      ```text Before (v20250224) theme={null}
      GET /users/{user_guid}/members/{member_guid}/oauth_window_uri
        ?client_redirect_url=https://example.com/callback
        &referral_source=APP
        &enable_app2app=true
        &ui_message_webview_url_scheme=mx
      ```
    </CodeGroup>

    In the v20260929 request body, `data_request` is required. `oauth` is optional, but if provided, it can't be empty.

    The response envelope key changes from `member` to `oauth` and includes a `member` Companion and `user` Companion. See the [Create OAuth Authorization URL endpoint documentation](/api-reference/platform-api/v20260929/reference/widgets/create-oauth-authorization-url) for the full request and response schemas.
  </Step>

  <Step title="Update Request Widget URL requests" id="widget-url-requests">
    Request Widget URL (POST `/users/{user_guid}/widget_urls`) rejects the following requests in v20260929. The response is unchanged.

    * **Mixed product settings:** You can't send `data_request` with the deprecated `mode`, `include_transactions`, or `include_identity` options. Set products with `data_request.products` only.
    * **`ui_message_version`:** This option is no longer supported. Remove it from your request.
    * **Mobile WebView without a redirect:** When `is_mobile_webview` is `true`, you must send either a `client_redirect_url` or a `ui_message_webview_url_scheme` other than `mx`.

    See the [Request Widget URL endpoint documentation](/api-reference/platform-api/v20260929/reference/widgets/request-widget-url) for the full request schema.
  </Step>

  <Step title="Update aggregation endpoints" id="aggregation-endpoints">
    Aggregation endpoints are renamed to align with the product names in `data_request.products`. All aggregation endpoints, including the deprecated paths, now return the `member_status` response, which adds a `products` companion and renames several fields. See the Member status changes in [Update response parsing](#layered-responses).

    All paths are relative to `/users/{user_identifier}/members/{member_identifier}/`.

    | v20250224 path | v20260929 path |
    | - | - |
    | `.../aggregate` | `.../transactions` (POST) |
    | `.../check_balance` | `.../balance` (POST) |
    | `.../extend_history` | `.../transaction_history` (POST) |
    | `.../identify` | `.../identity_verification` (POST) |
    | `.../verify` | `.../account_verification` (POST) |
    | `.../fetch_statements` | `.../statements` (POST) |
    | `.../fetch_rewards` | `.../rewards` (POST) |

    The v20250224 paths are deprecated. For sunset dates by version, see [Deprecations](./deprecations).
  </Step>

  <Step title="Revert date filters to ISO 8601" id="date-filters">
    Transaction date query parameters revert from Unix timestamps to ISO 8601 date strings (`YYYY-MM-DD`). This applies to all date filter parameters on List Transaction endpoints: `from_date`, `to_date`, `from_created_at`, `to_created_at`, `from_updated_at`, `to_updated_at`.

    <CodeGroup>
      ```text After (v20260929) theme={null}
      GET /users/{user_guid}/transactions?from_date=2024-01-01&to_date=2024-02-01
      ```

      ```text Before (v20250224) theme={null}
      GET /users/{user_guid}/transactions?from_date=1704067200&to_date=1706745600
      ```
    </CodeGroup>

    <Tip>
      **Upgrading from v20111101?**

      If you are upgrading directly from v20111101, which already uses ISO 8601 date strings, no change is needed.
    </Tip>
  </Step>

  <Step title="Stop using sunset and deprecated endpoints" id="deprecated-and-sunset-endpoints">
    The managed institution and managed member endpoints are sunset and return `410 Gone`. They have no direct API replacement. To send data held at your institution to MX, use [MDX Real Time](/products/connectivity/overview/held-data/mdx-real-time).

    The following endpoints are deprecated in v20260929. They still work, but move to their replacements before they are sunset:

    * `oauth_window_uri`: See [Replace the OAuth authorization URL endpoint](#oauth-authorization-url-endpoint).
    * `aggregate`, `check_balance`, `extend_history`, `identify`, `verify`, `fetch_statements`, and `fetch_rewards`: See [Update aggregation endpoints](#aggregation-endpoints).
    * `GET /users/{user_guid}/insights/{insight_guid}/scheduled_payments`: Use [List repeating transactions associated with an insight](/api-reference/platform-api/v20260929/reference/insights/list-all-repeating-transactions-associated-with-an-insight) instead.

    For sunset dates by version, see [Deprecations](./deprecations).
  </Step>

  <Step title="Validate your upgrade" id="validate-your-upgrade">
    Use the MX development (INT) environment to test your upgrade before updating production integrations. The INT environment shares the same code base as production but uses `https://int-api.mx.com` as the base URL.

    1. Update your `Accept-Version` header to `v20260929` in your INT environment requests.
    2. Verify your response parsing handles the Layered Responses structure (Base, Companions, Includes) for each resource you use.
    3. Confirm aggregation flows work with the new endpoint paths and `member_status` response.
    4. If using `includes[]`, verify the array syntax and new values return expected data on transaction endpoints.
    5. Test member creation and OAuth flows with the restructured request bodies.
    6. Request a widget URL with your production configuration and confirm the request succeeds.
  </Step>
</Steps>

## Upgrading from v20111101 to v20250224

### Key changes in v20250224

v20250224 standardizes how products are configured, modernizes request headers, and cleans up deprecated endpoints. Key changes include:

* **Enhanced institution search and filtering:** The `supported_products` array on List Institutions and Read Institution shows which products each institution supports, and you can filter institutions by product (for example, `supported_products[]=account_verification`).
* **Product-based aggregation on creation:** Set `data_request.products` on the Create Member and Request Widget URL endpoints to aggregate the products you need when a member is first created, instead of initiating aggregation manually.
* **Consistent product values:** `supported_products` and `data_request.products` share one set of values: `account_verification`, `identity_verification`, `transactions`, `transaction_history`, `statements`, and `investments`. Balance data is always included.
* **Dedicated version header:** Pass the version in the `Accept-Version` header and keep `Accept` set to `application/json`.

### Breaking changes in v20250224

The following changes require updates to your integration. Each links to the upgrade step with the details.

| Area | Breaking change | Upgrade step |
| - | - | - |
| Request headers | `Accept` must be `application/json`, and the version moves to a new `Accept-Version` header. | [Update request headers](#request-headers) |
| Institution product fields | The individual `supports_*` fields are removed from institution responses and List Institutions query parameters. Use the `supported_products` array instead. | [Update institution product fields](#institution-product-fields) |
| Widget URL configuration | `mode`, `include_identity`, and `include_transactions` on Request Widget URL are replaced by `data_request.products`. | [Set aggregation products with `data_request`](#data-request-products) |
| Deprecated fields | `skip_aggregation` and the Check Member Status `has_processed_*` fields still work in v20250224 but are removed in v20260929. | [Replace deprecated fields](#deprecated-fields) |
| Date filters | List Transactions date filters use Unix timestamps instead of ISO 8601 strings. Skip this change if you are continuing to v20260929. | [Update List Transactions date filters](#list-transactions-date-filters) |
| Sunset endpoints | Legacy widget URL and payment processor endpoints return `410 Gone`. Managed data endpoints are sunset on all versions. | [Stop using sunset endpoints](#sunset-endpoints) |

### Upgrade steps for v20250224

Complete these steps to move your integration from v20111101 to v20250224.

<Steps titleSize="h4">
  <Step title="Update request headers" id="request-headers">
    Modify your `Accept` request header to `application/json` and add an `Accept-Version` header set to `v20250224`.

    ```shell Example theme={null}
    curl -L -X POST 'https://int-api.mx.com/endpoint' \
      -H 'Content-Type: application/json' \
      -H 'Accept: application/json' \
      -H 'Accept-Version: v20250224' \
      -H 'Authorization: Basic BASE_64_ENCODING_OF{client_id:api_key}'
    ```

    <Accordion title="Unified Product Ordering beta users">
      [Unified Product Ordering](/products/connectivity/overview/intro-to-unified-product-ordering/) beta users must replace the beta header:

      ```text theme={null}
      -H 'Accept: application/vnd.mx.api.v1+json; version=v20250224'
      ```

      Use the new version header:

      ```text theme={null}
      -H 'Accept: application/json'
      -H 'Accept-Version: v20250224'
      ```
    </Accordion>
  </Step>

  <Step title="Update institution product fields" id="institution-product-fields">
    Update `institution` queries and responses to use the new `supported_products` array. The following individual fields are removed from both the institution response and the List Institutions query parameters:

    * `supports_account_identification`
    * `supports_account_statement`
    * `supports_account_verification`
    * `supports_transaction_history`

    Search and filter institutions by the products they support on **List Institutions** (GET `/institutions`) and **Read Institution** (GET `/institutions/{institution_code}`). See [Set aggregation products with `data_request`](#data-request-products) for accepted product values.

    <AccordionGroup>
      <Accordion title="Query example">
        ```shell theme={null}
        curl -X GET 'https://api.mx.com/institutions?supported_products[]=account_verification&supported_products[]=transactions' \
          -H 'Accept: application/json' \
          -H 'Accept-Version: v20250224' \
          -H 'Authorization: Basic BASE_64_ENCODING_OF{client_id:api_key}'
        ```
      </Accordion>

      <Accordion title="Response example">
        ```json theme={null}
        {
          "institution": {
            "code": "mxbank",
            "forgot_password_url": "https://example.url.mxbank.com/forgot-password",
            "forgot_username_url": "https://example.url.mxbank.com/forgot-username",
            "instructional_text": "Some instructional text ...",
            "iso_country_code": null,
            "medium_logo_url": "https://content.moneydesktop.com/storage/MD_Assets/Ipad%20Logos/100x100/default_100x100.png",
            "name": "MX Bank",
            "small_logo_url": "https://content.moneydesktop.com/storage/MD_Assets/Ipad%20Logos/50x50/default_50x50.png",
            "supported_products": [
              "account_verification",
              "identity_verification",
              "transactions",
              "transaction_history"
            ],
            "supports_oauth": false,
            "trouble_signing_in_url": null,
            "url": "https://www.mx.com"
          }
        }
        ```
      </Accordion>
    </AccordionGroup>

    <Warning>
      **Upgrading to v20260929?**

      In v20260929, `supported_products` is renamed to `products`, in both the institution response and the List Institutions filter. See the Institution changes in [Update response parsing](#layered-responses).
    </Warning>
  </Step>

  <Step title="Set aggregation products with `data_request`" id="data-request-products">
    Initiate the aggregation of specific products in the body of requests to create members and request Connect Widget URLs, instead of manually initiating aggregation when a member is first created.

    * **Create Member**: POST `/users/{user_guid}/members`
    * **Request Widget URL**: POST `/users/{user_guid}/widget_urls`. When requesting the Connect Widget URL, set `widget_url.data_request.products` instead of the following configuration parameters:
      * `mode`
      * `include_identity`
      * `include_transactions`

    The `supported_products` and `data_request.products` arrays accept the following values:

    | Product | Value |
    | :- | :- |
    | Instant Account Verification | `account_verification` |
    | Account Owner Identification | `identity_verification` |
    | Account Aggregation | `transactions` |
    | Extended History | `transaction_history` |
    | Statements | `statements` |
    | Investments | `investments` |

    <Note>
      Balance data is always included and does not need to be set.
    </Note>

    <AccordionGroup>
      <Accordion title="Create Member example">
        ```shell theme={null}
        curl -L -X POST 'https://int-api.mx.com/users/{user_guid}/members' \
          -H 'Content-Type: application/json' \
          -H 'Accept: application/json' \
          -H 'Accept-Version: v20250224' \
          -H 'Authorization: Basic BASE_64_ENCODING_OF{client_id:api_key}' \
          --data-raw '{
            "member": {
              "institution_code": "mxbank",
              "is_oauth": true,
              "metadata": "\"credentials_last_refreshed_at\": \"2015-10-15\""
            },
            "data_request": {
              "products": ["account_verification", "identity_verification", "transactions"]
            }
          }'
        ```
      </Accordion>

      <Accordion title="Request Widget URL example">
        ```shell theme={null}
        curl -L -X POST 'https://int-api.mx.com/users/{user_guid}/widget_urls' \
          -H 'Content-Type: application/json' \
          -H 'Accept: application/json' \
          -H 'Accept-Version: v20250224' \
          -H 'Authorization: Basic BASE_64_ENCODING_OF{client_id:api_key}' \
          --data-raw '{
            "widget_url": {
              "widget_type": "connect_widget",
              "data_request": {
                "products": ["account_verification", "identity_verification", "transactions"]
              }
            }
          }'
        ```
      </Accordion>
    </AccordionGroup>

    You can still initiate aggregation manually with these endpoints:

    * Aggregate Member
    * Balance Check
    * Extend History
    * Fetch Rewards
    * Fetch Statements
    * Identify Member
    * Verify Member
  </Step>

  <Step title="Replace deprecated fields" id="deprecated-fields">
    The `skip_aggregation` field is deprecated in favor of `data_request.products`, which provides more granular control over data aggregation. While still supported in v20250224, `skip_aggregation` is removed in v20260929. Migrate to `data_request.products`.

    The following fields in the **Check Member Status** endpoint response are deprecated:

    * `has_processed_account_numbers`
    * `has_processed_accounts`
    * `has_processed_transactions`
  </Step>

  <Step title="Update List Transactions date filters" id="list-transactions-date-filters">
    In v20250224, the `from_date`, `to_date`, `from_created_at`, `to_created_at`, `from_updated_at`, and `to_updated_at` query parameters on List Transactions endpoints accept Unix timestamps instead of the ISO 8601 strings (`YYYY-MM-DD`) used in v20111101.

    **Affected endpoints:**

    * GET `/users/{user_identifier}/transactions`
    * GET `/users/{user_identifier}/members/{member_identifier}/transactions`
    * GET `/users/{user_guid}/accounts/{account_guid}/transactions`
    * GET `/users/{user_identifier}/members/{member_identifier}/accounts/{account_identifier}/transactions`
    * GET `/users/{user_identifier}/tags/{tag_guid}/transactions`

    <Warning>
      **Upgrading to v20260929?**

      v20260929 reverts these parameters to ISO 8601 date strings. If you are upgrading from v20111101 to v20260929, skip this change and keep using ISO 8601 dates.

      If you are upgrading to v20250224 only, you will need to revert to ISO 8601 when you upgrade to v20260929.
    </Warning>
  </Step>

  <Step title="Stop using sunset endpoints" id="sunset-endpoints">
    The following endpoints are sunset on v20250224 and later, and return `410 Gone`:

    * `POST /users/{user_guid}/connect_widget_url`: Use [Request Widget URL](/api-reference/platform-api/v20260929/reference/widgets/request-widget-url) (`POST /users/{user_guid}/widget_urls`) instead.
    * `POST /payment_processor_authorization_code`: Use [Request an authorization code](/api-reference/platform-api/v20260929/reference/processor-token/request-an-authorization-code) (`POST /authorization_code`) instead.

    The managed data endpoints (`/managed_institutions` and the `/managed_members` tree) are sunset on all versions and return `410 Gone`. They have no direct API replacement. To send data held at your institution to MX, use [MDX Real Time](/products/connectivity/overview/held-data/mdx-real-time).

    For dates by version, see [Deprecations](./deprecations).
  </Step>
</Steps>
