INTRODUCTION

Your OpenAPI contract is perfect. Your idempotency store is atomic. But a single question remains: how do you change the API without breaking your TPPs? In open banking, versioning is not a developer convenience—it is a regulatory requirement. The CMA Order (Article 58) empowers the regulator to force a bank to maintain backward compatibility for a minimum period. The CDR Rules specify a 6‑month notice period for any breaking change.

This lesson deconstructs the mandatory headers that ensure traceability (x-fapi-interaction-id, x-fapi-financial-id, x-fapi-customer-ip-address), the semantic versioning strategy that OBIE v4.0 mandates, and the deprecation policy (RFC 8594) that governs sunsetting old endpoints. You will learn how to implement a versioned URI (/open-banking/v4/payments) versus a header‑based version (Accept‑Version: 4.0), and why URI versioning is preferred for regulatory clarity.

We will quantify the migration burden—how long TPPs have to migrate (minimum 6 months, typically 12‑18 months), and how to monitor version usage to identify laggards.


LEARNING OBJECTIVES

  1. Implement the mandatory FAPI headers—x-fapi-interaction-id (UUID for tracing), x-fapi-financial-id (ASPSP identifier), x-fapi-customer-ip-address (for fraud scoring), and x-fapi-auth-date (SCA timestamp)—and validate their presence at the API gateway level.

  2. Design a versioning strategy—using semantic versioning (e.g., v4.0.0 in the URI path) and maintaining at least 2 concurrent versions to satisfy the regulatory notice period (6 months minimum, 12 months recommended).

  3. Implement the Deprecation header (RFC 8594) and the Sunset header—communicating to TPPs when an endpoint will be retired, and returning 410 Gone after the sunset date.

  4. Calculate the migration window—computing the minimum overlap period based on regulatory requirements (CMA: 6 months; CDR: 6 months; PSD2: not specified, but industry standard is 12 months).

  5. Construct a version usage dashboard—monitoring which TPPs are using which versions, identifying stragglers, and proactively reaching out to ensure migration before sunset.


PART 1: MANDATORY FAPI HEADERS — The Traceability Stack

1.1 The Four Mandatory Headers (UK OBIE v4.0)

 
 
Header Example Purpose Regulatory Anchor
x-fapi-interaction-id 550e8400-e29b-41d4-a716-446655440000 End‑to‑end tracing across microservices OBIE v4.0, FAPI 1.0 Advanced
x-fapi-financial-id OBIE-UK-123456 Identifies the ASPSP (unique per institution) OBIE Directory Service
x-fapi-customer-ip-address 192.168.1.1 PSU’s IP for fraud detection and SCA risk EBA RTS on SCA (Art. 9)
x-fapi-auth-date 2026-08-03T12:34:56Z Timestamp of the SCA authentication (must be within the last 10 minutes) OBIE v4.0, FAPI 1.0 Advanced

1.2 OpenAPI Declaration

yaml
parameters:
  - name: x-fapi-interaction-id
    in: header
    required: true
    schema:
      type: string
      format: uuid
    description: |
      Interaction ID for end‑to‑end tracing. The ASPSP MUST echo this value
      in the response header and include it in audit logs.
  - name: x-fapi-financial-id
    in: header
    required: true
    schema:
      type: string
      pattern: '^OBIE-UK-[0-9]{6}$'
    description: |
      Financial institution ID assigned by the OBIE Directory Service.
  - name: x-fapi-customer-ip-address
    in: header
    required: false  # Optional in some endpoints, but recommended
    schema:
      type: string
      format: ipv4
    description: |
      PSU's IPv4 address, used for fraud scoring and SCA risk assessment.
  - name: x-fapi-auth-date
    in: header
    required: false
    schema:
      type: string
      format: date-time
    description: |
      ISO 8601 timestamp of the SCA authentication (≤10 minutes ago).

1.3 Validation Logic at the API Gateway

python
import uuid
import re
from datetime import datetime, timedelta

def validate_fapi_headers(headers):
    # 1. Validate x-fapi-interaction-id (must be a valid UUID)
    interaction_id = headers.get('x-fapi-interaction-id')
    if not interaction_id:
        raise ValidationError('Missing x-fapi-interaction-id')
    try:
        uuid.UUID(interaction_id)
    except ValueError:
        raise ValidationError('Invalid x-fapi-interaction-id format')

    # 2. Validate x-fapi-financial-id (pattern: OBIE-UK-XXXXXX)
    financial_id = headers.get('x-fapi-financial-id')
    if not financial_id:
        raise ValidationError('Missing x-fapi-financial-id')
    if not re.match(r'^OBIE-UK-[0-9]{6}$', financial_id):
        raise ValidationError('Invalid x-fapi-financial-id format')

    # 3. Validate x-fapi-auth-date (if provided, must be within 10 minutes)
    auth_date = headers.get('x-fapi-auth-date')
    if auth_date:
        try:
            auth_time = datetime.fromisoformat(auth_date.replace('Z', '+00:00'))
            now = datetime.now(datetime.timezone.utc)
            if (now - auth_time).total_seconds() > 600:  # 10 minutes
                raise ValidationError('x-fapi-auth-date is too old (>10 minutes)')
        except ValueError:
            raise ValidationError('Invalid x-fapi-auth-date format')

    return True

Latency overhead: Validation is string parsing (no network calls). Total overhead ≤0.5ms (p95).

PART 2: VERSIONING STRATEGY — URI Path vs. Header

2.1 URI Path Versioning (Recommended)

  • Format: /open-banking/v{version}/{resource}

  • Example: /open-banking/v4/payments

  • Pros: Clear, visible, easily auditable. The version is part of the resource identity.

  • Cons: Adds path depth; slightly increases routing latency (+15µs for trie routing).

Regulatory advantage: A regulator can see the version from the URL in logs without parsing headers.

2.2 Header‑Based Versioning (Not Recommended)

  • Format: Accept-Version: 4.0

  • Example: Accept-Version: 4.0 in the request header.

  • Pros: Cleaner URIs.

  • Cons: Not visible in logs (requires header parsing); TPPs often forget to set the header, defaulting to the latest version (breaking change).

Industry consensus: OBIE, CDR, and FDX all use URI path versioning.

2.3 Semantic Versioning vs. Date Versioning

 
 
Approach Example Pros Cons
Semantic v4.0.0, v4.1.0 Clear, incremental Major version bumps are ambiguous
Date v2026-08-01 Explicit, no ambiguity Longer URIs
Major.Minor v4 (major), v4.1 (minor) Balance of clarity and brevity Used by OBIE (v4.0)

Recommendation: Use major version only in the URI (e.g., /v4), and handle minor changes (additive) within the same major version.


PART 3: DEPRECATION AND SUNSET — RFC 8594

3.1 The Deprecation Header

RFC 8594 defines the Deprecation header, which indicates that an endpoint is deprecated and will be removed in the future.

Example:

text
Deprecation: true
Sunset: Wed, 01 Jan 2028 00:00:00 GMT

OpenAPI declaration:

yaml
paths:
  /v3/payments:
    get:
      summary: Get payment status (DEPRECATED)
      deprecated: true
      responses:
        '200':
          headers:
            Deprecation:
              schema:
                type: boolean
                example: true
            Sunset:
              schema:
                type: string
                format: date-time
                example: '2028-01-01T00:00:00Z'

3.2 The Sunset Policy

The OBIE v4.0 mandates that any deprecated endpoint must remain available for at least 6 months after the deprecation notice. The CDR Rules specify 6 months as well. The industry best practice is 12 months to allow TPPs ample time to migrate.

Sunset date calculation:

text
Sunset = Deprecation_Date + 12 months

3.3 Returning 410 Gone After Sunset

After the sunset date, the ASPSP must return 410 Gone for the deprecated endpoint.

Response:

json
{
  "ErrorCode": "GONE",
  "ErrorDescription": "This API version has been retired. Please migrate to /v4/payments.",
  "MigrationDocumentation": "https://developer.bank.com/migration/v3-to-v4"
}

PART 4: MIGRATION MONITORING AND COMPLIANCE DASHBOARD

4.1 Version Usage Metrics

At the API gateway, log the version used for every request:

json
{
  "timestamp": "2026-08-03T12:34:56Z",
  "client_id": "TPP-12345",
  "endpoint": "/v3/payments",
  "version": "v3",
  "status_code": 200
}

4.2 Dashboard Metrics

 
 
Metric Threshold Alert
v3 traffic % >20% of total traffic Alert at 6 months before sunset
v3 traffic count >100 RPS Alert if high, indicating a major TPP hasn’t migrated
Latest version adoption >80% within 6 months of release Alert if below threshold

4.3 Proactive Outreach

If a TPP continues to use a deprecated version after 9 months, the API gateway can inject a warning header:

text
Warning: 299 - "This API version will be retired on 2028-01-01. Please migrate to /v4."

The TPP receives this warning on every request, encouraging migration.


CLOSING — OPERATIONAL RISK OF POOR VERSIONING

If the ASPSP removes an endpoint without the regulatory notice period:

  • TPPs break → complaints to the CMA → Article 58 direction.

  • Regulatory breach → fines and public reprimand.

  • Reputational damage → TPPs avoid the bank’s API.

Key takeaways:

  • x-fapi-* headers are mandatory for traceability and fraud detection.

  • URI path versioning (/v4/resource) is the regulatory standard.

  • Deprecation must be announced at least 6‑12 months before sunset.

  • Monitor version usage and proactively reach out to TPPs.

 

 
Â