openapi: 3.1.0
info:
  title: YCMT EU Partner Customer-Context Core API
  version: 1.0.0
  summary: Partner-facing customer-context API for YCMT EU.
  contact:
    name: YesCash Group Engineering
  license:
    name: Confidential — YesCash Group internal and per-partner-onboarding-NDA distribution
    url: https://docs.yescash.example/license
  description: Partner-facing OpenAPI contract for YCMT EU. This file describes the
    request and response interface that partner applications use. It intentionally
    omits YCMT internal implementation details. The human-readable Partner Developer
    API Guide remains the primary implementation companion for examples and flow guidance.
servers:
- url: https://api.eu.yescash.example
  description: YCMT EU production host placeholder. The production host is confirmed
    during partner activation.
- url: https://sandbox.api.eu.yescash.example
  description: YCMT EU sandbox host placeholder. The sandbox host is provided during
    partner onboarding.
tags:
- name: Profile
- name: KYC
- name: Quotes
- name: Beneficiaries
- name: Transfers
components:
  securitySchemes:
    apimSubscriptionKey:
      type: apiKey
      in: header
      name: Ocp-Apim-Subscription-Key
    bearerAuth:
      type: http
      scheme: bearer
      bearerFormat: JWT
  parameters:
    XCorrelationIdHeader:
      name: X-Correlation-Id
      in: header
      required: false
      schema:
        type: string
        format: uuid
        example: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
    XIdempotencyKeyHeader:
      name: X-Idempotency-Key
      in: header
      required: true
      schema:
        type: string
        format: uuid
        example: 5f9d4f6a-2c1b-4e8d-9a3f-7b8c1d2e4a5f
    AcceptLanguageHeader:
      name: Accept-Language
      in: header
      required: false
      schema:
        type: string
        example: es-ES, en;q=0.5
    QuoteIdPathParam:
      name: quoteId
      in: path
      required: true
      schema:
        type: string
        example: Q-01HXBK0R1S4U6V8X0Z2A4C6E8G
    BeneficiaryIdPathParam:
      name: beneficiaryId
      in: path
      required: true
      schema:
        type: string
        example: BEN-01HX9F2J7K3M5N7P9Q1R3T5V7W
    TransferIdPathParam:
      name: transferId
      in: path
      required: true
      schema:
        type: string
        example: TRF-01HX9F2J7K3M5N7P9Q1R3T5V7W
    KycSessionIdPathParam:
      name: kycSessionId
      in: path
      required: true
      schema:
        type: string
        example: KS-01HX9F2J7K3M5N7P9Q1R3T5V7W
  headers:
    XCorrelationIdResponseHeader:
      schema:
        type: string
        format: uuid
      example: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
    LocationHeader:
      schema:
        type: string
      example: /v1/core/transfers/TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
    RetryAfterHeader:
      schema:
        type: integer
  schemas:
    Error:
      type: object
      required:
      - error
      properties:
        error:
          type: object
          required:
          - code
          - message
          - correlationId
          properties:
            code:
              type: string
              example: quote.expired
            message:
              type: string
              example: Quote has expired.
            correlationId:
              type: string
              format: uuid
              example: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
            details: {}
    ValidationIssue:
      type: object
      required:
      - field
      - code
      properties:
        field:
          type: string
          example: dateOfBirth
        code:
          type: string
          example: validation.dateFormat
        message:
          type: string
          example: dateOfBirth must be ISO 8601 date format YYYY-MM-DD
    RemediationHintDetails:
      type: object
      properties:
        remediationHint:
          type: string
          example: retry_later
    CustomerStatusDetails:
      type: object
      properties:
        currentStatus:
          $ref: '#/components/schemas/CustomerStatus'
        remediationHint:
          type: string
          example: contact_support
    QuoteExpiredDetails:
      type: object
      properties:
        quoteId:
          type: string
          example: Q-01HXFP6W7X9Z1B3D5F7H9J1L3N5
        quoteExpiredAt:
          type: string
          format: date-time
          example: 2026-05-14 11:01:01+00:00
        remediationHint:
          type: string
          example: retry_later
    BeneficiaryStateDetails:
      type: object
      properties:
        beneficiaryId:
          type: string
        currentState:
          $ref: '#/components/schemas/BeneficiaryState'
        remediationHint:
          type: string
          example: await_beneficiary_verification
    DeviceLockoutDetails:
      type: object
      properties:
        retryAfterSeconds:
          type: integer
          minimum: 1
        remediationHint:
          type: string
          example: contact_support
    PasswordPolicyRule:
      type: string
      enum:
      - MIN_LENGTH_10
      - REQUIRE_UPPERCASE
      - REQUIRE_LOWERCASE
      - REQUIRE_DIGIT
      - REQUIRE_SYMBOL
    CustomerStatus:
      type: string
      enum:
      - PENDING
      - VALID
      - MONITORED
      - RESTRICTED
      - BLOCKED
      - CLOSED
    KycStatus:
      type: string
      enum:
      - NOT_STARTED
      - IN_PROGRESS
      - COMPLETED
      - REJECTED
      - REMEDIATION_REQUIRED
    SubscriptionStatus:
      type: string
      enum:
      - active
      - suspended
      - closed
    TransferState:
      type: string
      enum:
      - registered
      - onreview
      - validated
      - funding
      - funded
      - topay
      - reqpay
      - suspended
      - paid
      - aborted
      - rejected
      - expired
      - canceled
    BeneficiaryState:
      type: string
      enum:
      - PENDING
      - VALID
      - MONITORED
      - BLOCKED
      - ARCHIVED
    BeneficiaryRelationship:
      type: string
      enum:
      - SPOUSE
      - CHILD
      - PARENT
      - SIBLING
      - OTHER_FAMILY
      - BUSINESS_CONTACT
      - FRIEND
      - SELF
      - OTHER
    PayoutMethodType:
      type: string
      enum:
      - BANK_TRANSFER
      - CASH_PICKUP
      - WALLET_TRANSFER
      - MOBILE_MONEY
    PurposeOfTransfer:
      type: string
      enum:
      - FAMILY_SUPPORT
      - SALARY
      - BUSINESS_PAYMENT
      - GIFT
      - EDUCATION
      - MEDICAL
      - PROPERTY
      - OTHER
    CancellationReason:
      type: string
      enum:
      - CHANGED_MIND
      - WRONG_RECIPIENT
      - WRONG_AMOUNT
      - TAKING_TOO_LONG
      - RECIPIENT_NOT_AVAILABLE
      - OTHER
    CancellationOutcome:
      type: string
      enum:
      - ABORTED_PRE_FUNDING
      - CANCELED_PRE_NETWORK
      - NETWORK_CANCELLATION_PENDING
      - NETWORK_CANCELLATION_SUCCESS
      - NETWORK_ALREADY_PAID
      - NETWORK_IN_PROGRESS_RETRY_ALLOWED
      - SUSPENDED_CANCELLED
    RefundStatus:
      type: string
      enum:
      - REFUND_INITIATED
      - REFUND_PENDING
      - REFUND_SUCCEEDED
      - REFUND_FAILED
      - REFUND_FAILED_REQUIRES_ALTERNATE_MECHANISM
    RefundMethod:
      type: string
      enum:
      - ORIGINAL_PAYMENT_METHOD
    KycSessionState:
      type: string
      enum:
      - IN_PROGRESS
      - CLOSED
      - EXPIRED
    KycSessionPurpose:
      type: string
      enum:
      - INITIAL_KYC
      - RESUBMISSION
    FundingSessionStatus:
      type: string
      enum:
      - pending_customer_action
      - completed
      - failed
      - expired
    IdentifierType:
      type: string
      enum:
      - EMAIL
      - PHONE
    Gender:
      type: string
      enum:
      - MALE
      - FEMALE
      - OTHER
      - NOT_DISCLOSED
    NextStep:
      type: string
      enum:
      - SUBMIT_PROFILE_ATTRIBUTES
      - COMPLETE_KYC_CAPTURE
      - AWAIT_FAST_CHECK
      - AWAIT_OPERATOR_REVIEW
      - AWAIT_DEVICE_AUTHENTICATION
      - OPEN_FUNDING_WEBVIEW
      - AWAIT_FUNDING
      - AWAIT_NETWORK
      - WAIT_REFUND
      - KYC_REFRESH_REQUIRED
      - USE_OTHER_BENEFICIARY
      - CONTACT_SUPPORT
      - TRANSFER_CONFIRMATION_REQUIRED
    CustomerActionExpected:
      type: string
      enum:
      - SUBMIT_PROFILE
      - COMPLETE_KYC
      - SELECT_BENEFICIARY
      - CONFIRM_TRANSFER
      - OPEN_FUNDING_WEBVIEW
      - WAIT
      - WAIT_REFUND
      - NONE
    StructuredAddress:
      type: object
      required:
      - addressLine1
      - city
      - country
      properties:
        addressLine1:
          type: string
          maxLength: 200
        addressLine2:
          type: string
          nullable: true
          maxLength: 200
        city:
          type: string
          maxLength: 100
        region:
          type: string
          nullable: true
          maxLength: 100
        postalCode:
          type: string
          nullable: true
          maxLength: 30
        country:
          type: string
          minLength: 3
          maxLength: 3
    PlaceOfBirth:
      type: object
      required:
      - city
      - country
      properties:
        city:
          type: string
        country:
          type: string
          minLength: 3
          maxLength: 3
    IdentifierSummary:
      type: object
      required:
      - identifierId
      - identifierType
      - identifierMasked
      - verifiedAt
      - canRemove
      properties:
        identifierId:
          type: string
          example: ID-01HX9F2J7K3M5N7P9Q1R3T5V7W
        identifierType:
          $ref: '#/components/schemas/IdentifierType'
        identifierMasked:
          type: string
          example: a****@example.com
        verifiedAt:
          type: string
          format: date-time
        canRemove:
          type: boolean
    Corridor:
      type: object
      required:
      - originCountry
      - destinationCountry
      - payoutMethod
      properties:
        originCountry:
          type: string
          minLength: 3
          maxLength: 3
          example: ESP
        destinationCountry:
          type: string
          minLength: 3
          maxLength: 3
          example: MAR
        payoutMethod:
          type: string
          example: bank_account
    PayoutMethodRequest:
      type: object
      required:
      - methodType
      properties:
        methodType:
          $ref: '#/components/schemas/PayoutMethodType'
        destinationIdentifier:
          type: string
          nullable: true
        payoutMethodId:
          type: string
          nullable: true
    PayoutMethodMasked:
      type: object
      required:
      - payoutMethodId
      - methodType
      - corridor
      - destinationIdentifierMasked
      properties:
        payoutMethodId:
          type: string
          example: PM-01HX9F2J7K3M5N7P9Q1R3T5V7W
        methodType:
          $ref: '#/components/schemas/PayoutMethodType'
        corridor:
          type: string
          example: ES-MA
        destinationIdentifierMasked:
          type: string
          example: '****1332'
        addedAt:
          type: string
          format: date-time
        archived:
          type: boolean
    PayoutMethodSummary:
      type: object
      required:
      - payoutMethodId
      - methodType
      - corridor
      - destinationIdentifierMasked
      - addedAt
      - archived
      properties:
        payoutMethodId:
          type: string
        methodType:
          $ref: '#/components/schemas/PayoutMethodType'
        corridor:
          type: string
        destinationIdentifierMasked:
          type: string
        addedAt:
          type: string
          format: date-time
        archived:
          type: boolean
    StateHistoryEntry:
      type: object
      required:
      - state
      - transitionedAt
      - reasonCode
      properties:
        state:
          $ref: '#/components/schemas/TransferState'
        transitionedAt:
          type: string
          format: date-time
        reasonCode:
          type: string
          example: TRF_CHECK_PASSED
    FundingSession:
      type: object
      required:
      - fundingSessionId
      - fundingWebviewUrl
      - expiresAt
      properties:
        fundingSessionId:
          type: string
          example: FND-01HXKT1B2C4D6F8H0J2L4N6P8R0
        fundingWebviewUrl:
          type: string
          format: uri
          example: https://funding.eu.yescash.example/sessions/FND-01HXKT1B2C4D6F8H0J2L4N6P8R0
        expiresAt:
          type: string
          format: date-time
    CancellationDetail:
      type: object
      properties:
        cancellationOutcome:
          $ref: '#/components/schemas/CancellationOutcome'
        cancellationReason:
          $ref: '#/components/schemas/CancellationReason'
        cancelRequestedAt:
          type: string
          format: date-time
        canceledAt:
          type: string
          format: date-time
          nullable: true
        networkCancellationExpectedBy:
          type: string
          format: date-time
          nullable: true
    RefundDetail:
      type: object
      properties:
        refundStatus:
          $ref: '#/components/schemas/RefundStatus'
        estimatedRefundCompletionBy:
          type: string
          format: date-time
        refundMethod:
          $ref: '#/components/schemas/RefundMethod'
    ProfileSubmitRequest:
      type: object
      required:
      - firstName
      - lastName
      - dateOfBirth
      - nationality
      - residenceCountry
      - residenceAddress
      properties:
        firstName:
          type: string
          maxLength: 100
          example: Aicha
        lastName:
          type: string
          maxLength: 100
          example: El Amrani
        middleNames:
          type: array
          maxItems: 5
          items:
            type: string
            maxLength: 100
        dateOfBirth:
          type: string
          format: date
          example: '1990-03-15'
        nationality:
          type: string
          minLength: 3
          maxLength: 3
          example: MAR
        residenceCountry:
          type: string
          minLength: 3
          maxLength: 3
          example: ESP
        residenceAddress:
          $ref: '#/components/schemas/StructuredAddress'
        gender:
          $ref: '#/components/schemas/Gender'
        placeOfBirth:
          $ref: '#/components/schemas/PlaceOfBirth'
    ProfileSubmitResponse:
      type: object
      required:
      - status
      - kycRequired
      - nextStep
      properties:
        status:
          $ref: '#/components/schemas/CustomerStatus'
        kycRequired:
          type: boolean
        nextStep:
          $ref: '#/components/schemas/NextStep'
    ProfileReadResponse:
      type: object
      required:
      - subscriptionId
      - status
      - kycStatus
      - transactability
      - customerActionExpected
      - profile
      - identifiers
      properties:
        subscriptionId:
          type: string
          example: SUB-01HX9F2J7K3M5N7P9Q1R3T5V7W
        status:
          $ref: '#/components/schemas/CustomerStatus'
        statusOperationalHint:
          type: string
          nullable: true
        kycStatus:
          $ref: '#/components/schemas/KycStatus'
        transactability:
          type: boolean
        customerActionExpected:
          type: boolean
        profile:
          type: object
          required:
          - firstName
          - lastName
          - dateOfBirth
          - nationality
          - residenceCountry
          properties:
            firstName:
              type: string
            lastName:
              type: string
            middleNames:
              type: array
              items:
                type: string
            dateOfBirth:
              type: string
              format: date
            nationality:
              type: string
            residenceCountry:
              type: string
            residenceAddress:
              $ref: '#/components/schemas/StructuredAddress'
            gender:
              $ref: '#/components/schemas/Gender'
            placeOfBirth:
              $ref: '#/components/schemas/PlaceOfBirth'
        identifiers:
          type: array
          items:
            $ref: '#/components/schemas/IdentifierSummary'
    KycSessionCreateResponse:
      type: object
      required:
      - kycSessionId
      - webviewUrl
      - expiresAt
      - closureCallback
      properties:
        kycSessionId:
          type: string
          example: KS-01HX9F2J7K3M5N7P9Q1R3T5V7W
        webviewUrl:
          type: string
          format: uri
          example: https://kyc.eu.yescash.example/session/abc123def456ghi789jkl012mno345pqr
        expiresAt:
          type: string
          format: date-time
        closureCallback:
          type: object
          required:
          - scheme
          - messageOrigin
          properties:
            scheme:
              type: string
              example: yescash-partner
            messageOrigin:
              type: string
              format: uri
              example: https://kyc.eu.yescash.example
    KycSessionReadResponse:
      type: object
      required:
      - kycSessionId
      - sessionState
      - openedAt
      - expiresAt
      properties:
        kycSessionId:
          type: string
        sessionState:
          $ref: '#/components/schemas/KycSessionState'
        openedAt:
          type: string
          format: date-time
        closedAt:
          type: string
          format: date-time
          nullable: true
        expiresAt:
          type: string
          format: date-time
    QuoteCreateRequest:
      type: object
      required:
      - originAmount
      - originCurrency
      - destinationCurrency
      - beneficiaryId
      properties:
        originAmount:
          type: string
          pattern: ^[0-9]+\.[0-9]{6}$
          example: '100.000000'
        originCurrency:
          type: string
          minLength: 3
          maxLength: 3
          example: EUR
        destinationCurrency:
          type: string
          minLength: 3
          maxLength: 3
          example: MAD
        beneficiaryId:
          type: string
    QuoteResponse:
      type: object
      required:
      - quoteId
      - originAmount
      - originCurrency
      - destinationAmount
      - destinationCurrency
      - fxRate
      - principalFee
      - partnerFee
      - totalCustomerCost
      - totalCustomerCostCurrency
      - quoteValidUntil
      - quoteSignature
      - corridor
      properties:
        quoteId:
          type: string
          example: Q-01HXBK0R1S4U6V8X0Z2A4C6E8G
        originAmount:
          type: string
          example: '100.000000'
        originCurrency:
          type: string
          example: EUR
        destinationAmount:
          type: string
          example: '1053.000000'
        destinationCurrency:
          type: string
          example: MAD
        fxRate:
          type: string
          example: '10.530000'
        principalFee:
          type: string
          example: '1.500000'
        partnerFee:
          type: string
          example: '0.500000'
        totalCustomerCost:
          type: string
          example: '102.000000'
        totalCustomerCostCurrency:
          type: string
          example: EUR
        quoteValidUntil:
          type: string
          format: date-time
        quoteSignature:
          type: string
          example: eyJ...<JWS-truncated>...
        quoteStatus:
          type: string
          enum:
          - active
          - expired
          - accepted
          - superseded
        corridor:
          $ref: '#/components/schemas/Corridor'
    QuoteAcceptRequest:
      type: object
      required:
      - disclosureToken
      - purposeOfTransfer
      properties:
        disclosureToken:
          type: string
          example: DT-01HXBL2S3T5V7X9Z1A3C5E7G9I
        purposeOfTransfer:
          $ref: '#/components/schemas/PurposeOfTransfer'
    QuoteAcceptResponse:
      type: object
      required:
      - transferId
      - transferStatus
      - quoteId
      - acceptedAt
      - nextStep
      properties:
        transferId:
          type: string
          example: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
        transferStatus:
          $ref: '#/components/schemas/TransferState'
        quoteId:
          type: string
        acceptedAt:
          type: string
          format: date-time
        nextStep:
          $ref: '#/components/schemas/NextStep'
    DisclosureResponse:
      type: object
      required:
      - disclosureToken
      - disclosureVersion
      - disclosureLanguage
      - disclosureText
      - regulatoryAnchors
      - issuedAt
      - expiresAt
      properties:
        disclosureToken:
          type: string
          example: DT-01HX9F2J7K3M5N7P9Q1R3T5V7W
        disclosureVersion:
          type: string
          example: EU-ES-2026.04
        disclosureLanguage:
          type: string
          example: es-ES
        disclosureText:
          type: string
        regulatoryAnchors:
          type: array
          items:
            type: string
        totalConsumerCost:
          type: string
        sendAmount:
          type: string
        sendCurrency:
          type: string
        receiveAmount:
          type: string
        receiveCurrency:
          type: string
        fxRate:
          type: string
        issuedAt:
          type: string
          format: date-time
        expiresAt:
          type: string
          format: date-time
    BeneficiaryCreateRequest:
      type: object
      required:
      - firstName
      - lastName
      properties:
        firstName:
          type: string
          maxLength: 100
        lastName:
          type: string
          maxLength: 100
        dateOfBirth:
          type: string
          format: date
        address:
          $ref: '#/components/schemas/StructuredAddress'
        nationality:
          type: string
          minLength: 2
          maxLength: 2
        countryOfResidence:
          type: string
          minLength: 2
          maxLength: 2
        relationshipToCustomer:
          $ref: '#/components/schemas/BeneficiaryRelationship'
    BeneficiaryCreateResponse:
      type: object
      required:
      - beneficiaryId
      - state
      - createdAt
      properties:
        beneficiaryId:
          type: string
          example: BEN-01HX9F2J7K3M5N7P9Q1R3T5V7W
        state:
          $ref: '#/components/schemas/BeneficiaryState'
        createdAt:
          type: string
          format: date-time
    BeneficiarySummary:
      type: object
      required:
      - beneficiaryId
      - firstName
      - lastName
      - state
      - createdAt
      - payoutMethodCount
      properties:
        beneficiaryId:
          type: string
        firstName:
          type: string
        lastName:
          type: string
        state:
          $ref: '#/components/schemas/BeneficiaryState'
        createdAt:
          type: string
          format: date-time
        lastUsedAt:
          type: string
          format: date-time
          nullable: true
        payoutMethodCount:
          type: integer
          minimum: 0
    BeneficiaryListResponse:
      type: object
      required:
      - items
      properties:
        items:
          type: array
          items:
            $ref: '#/components/schemas/BeneficiarySummary'
        nextCursor:
          type: string
          nullable: true
    BeneficiaryDetailResponse:
      type: object
      required:
      - beneficiaryId
      - firstName
      - lastName
      - state
      - createdAt
      - stateChangedAt
      - payoutMethods
      properties:
        beneficiaryId:
          type: string
        firstName:
          type: string
        lastName:
          type: string
        dateOfBirth:
          type: string
          format: date
          nullable: true
        address:
          $ref: '#/components/schemas/StructuredAddress'
        nationality:
          type: string
          nullable: true
        countryOfResidence:
          type: string
          nullable: true
        relationshipToCustomer:
          $ref: '#/components/schemas/BeneficiaryRelationship'
        state:
          $ref: '#/components/schemas/BeneficiaryState'
        createdAt:
          type: string
          format: date-time
        stateChangedAt:
          type: string
          format: date-time
        lastUsedAt:
          type: string
          format: date-time
          nullable: true
        customerActionExpected:
          type: string
          nullable: true
        payoutMethods:
          type: array
          items:
            $ref: '#/components/schemas/PayoutMethodSummary'
    BeneficiaryArchiveResponse:
      type: object
      required:
      - beneficiaryId
      - state
      - archivedAt
      properties:
        beneficiaryId:
          type: string
        state:
          $ref: '#/components/schemas/BeneficiaryState'
        archivedAt:
          type: string
          format: date-time
    TransferSubmitRequest:
      type: object
      required:
      - beneficiaryId
      - payoutMethod
      - purposeOfTransfer
      properties:
        beneficiaryId:
          type: string
        payoutMethod:
          $ref: '#/components/schemas/PayoutMethodRequest'
        purposeOfTransfer:
          $ref: '#/components/schemas/PurposeOfTransfer'
    TransferSubmitResponse:
      type: object
      required:
      - transferId
      - transferStatus
      - beneficiaryId
      - payoutMethod
      - purposeOfTransfer
      - submittedAt
      - fastCheckExpectedBy
      - nextStep
      properties:
        transferId:
          type: string
        transferStatus:
          $ref: '#/components/schemas/TransferState'
        beneficiaryId:
          type: string
        payoutMethod:
          $ref: '#/components/schemas/PayoutMethodMasked'
        purposeOfTransfer:
          $ref: '#/components/schemas/PurposeOfTransfer'
        submittedAt:
          type: string
          format: date-time
        fastCheckExpectedBy:
          type: string
          format: date-time
        nextStep:
          $ref: '#/components/schemas/NextStep'
    TransferCancelRequest:
      type: object
      required:
      - cancellationReason
      properties:
        cancellationReason:
          $ref: '#/components/schemas/CancellationReason'
    TransferCancelResponse:
      type: object
      required:
      - transferId
      - transferStatus
      - cancellationOutcome
      properties:
        transferId:
          type: string
        transferStatus:
          $ref: '#/components/schemas/TransferState'
        cancellationOutcome:
          $ref: '#/components/schemas/CancellationOutcome'
        canceledAt:
          type: string
          format: date-time
          nullable: true
        nextStep:
          allOf:
          - $ref: '#/components/schemas/NextStep'
          nullable: true
        customerActionExpected:
          allOf:
          - $ref: '#/components/schemas/CustomerActionExpected'
          nullable: true
        networkCancellationExpectedBy:
          type: string
          format: date-time
          nullable: true
        refund:
          allOf:
          - $ref: '#/components/schemas/RefundDetail'
          nullable: true
    DeviceAssertion:
      type: object
      required:
      - deviceAssertion
      properties:
        deviceAssertion:
          type: string
          example: eyJhbGciOiJSUzI1NiIsImtpZCI6ImRldmljZS1rZXktMjAyNi0wNS0xMVQxNC01OFoiLCJ0eXAiOiJKV1QifQ.eyJ0cmFuc2Zlcl9pZCI6IlRSRi0wMUhYOUYySjdLM001TjdQOVExUjNUNVY3VyIsImFtb3VudCI6IjEwMC4wMCIsImN1cnJlbmN5IjoiRVVSIiwiYmVuZWZpY2lhcnlfaWQiOiJCRU4tMDFIWDlGMko3SzNNNU43UDlRMVIzVDVWN1ciLCJkZXZpY2VfaWQiOiJERVYtMDFIWDlGMko3SzNNNU43UDlRMVIzVDVWN1ciLCJub25jZSI6Ii4uLiIsImNoYWxsZW5nZSI6Ii4uLiIsImlhdCI6MTcxNTYwODgyMn0.signature_bytes_omitted
    TransferConfirmResponse:
      type: object
      required:
      - transferId
      - transferStatus
      - confirmedAt
      - nextStep
      - fundingSession
      properties:
        transferId:
          type: string
        transferStatus:
          $ref: '#/components/schemas/TransferState'
        confirmedAt:
          type: string
          format: date-time
        nextStep:
          $ref: '#/components/schemas/NextStep'
        fundingSession:
          $ref: '#/components/schemas/FundingSession'
    TransferDetailResponse:
      type: object
      required:
      - transferId
      - transferStatus
      - originAmount
      - originCurrency
      - destinationAmount
      - destinationCurrency
      - beneficiaryId
      - createdAt
      - transferStateChangedAt
      - customerActionExpected
      properties:
        transferId:
          type: string
        transferStatus:
          $ref: '#/components/schemas/TransferState'
        transferStateChangedAt:
          type: string
          format: date-time
        originAmount:
          type: string
        originCurrency:
          type: string
        destinationAmount:
          type: string
        destinationCurrency:
          type: string
        fxRate:
          type: string
        principalFee:
          type: string
        partnerFee:
          type: string
        totalCustomerCost:
          type: string
        totalCustomerCostCurrency:
          type: string
        beneficiaryId:
          type: string
        payoutMethod:
          $ref: '#/components/schemas/PayoutMethodMasked'
        purposeOfTransfer:
          $ref: '#/components/schemas/PurposeOfTransfer'
        quoteId:
          type: string
        createdAt:
          type: string
          format: date-time
        submittedAt:
          type: string
          format: date-time
          nullable: true
        confirmedAt:
          type: string
          format: date-time
          nullable: true
        transferExpiresAt:
          type: string
          format: date-time
          nullable: true
        nextStep:
          allOf:
          - $ref: '#/components/schemas/NextStep'
          nullable: true
        customerActionExpected:
          $ref: '#/components/schemas/CustomerActionExpected'
        confirmationChallenge:
          type: string
          nullable: true
        confirmationChallengeExpiresAt:
          type: string
          format: date-time
          nullable: true
        fundingSession:
          allOf:
          - $ref: '#/components/schemas/FundingSession'
          nullable: true
        cancellation:
          allOf:
          - $ref: '#/components/schemas/CancellationDetail'
          nullable: true
        refund:
          allOf:
          - $ref: '#/components/schemas/RefundDetail'
          nullable: true
        stateHistory:
          type: array
          items:
            $ref: '#/components/schemas/StateHistoryEntry'
    TransferSummary:
      type: object
      required:
      - transferId
      - transferStatus
      - createdAt
      - originAmount
      - originCurrency
      - destinationAmount
      - destinationCurrency
      - beneficiaryId
      properties:
        transferId:
          type: string
        transferStatus:
          $ref: '#/components/schemas/TransferState'
        transferStateChangedAt:
          type: string
          format: date-time
        createdAt:
          type: string
          format: date-time
        originAmount:
          type: string
        originCurrency:
          type: string
        destinationAmount:
          type: string
        destinationCurrency:
          type: string
        beneficiaryId:
          type: string
    TransferListResponse:
      type: object
      required:
      - items
      properties:
        items:
          type: array
          items:
            $ref: '#/components/schemas/TransferSummary'
        nextCursor:
          type: string
          nullable: true
  responses:
    BadRequest:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            fieldInvalid:
              summary: validation.fieldInvalid — per-field validation failure
              value:
                error:
                  code: validation.fieldInvalid
                  message: One or more fields failed validation.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    issues:
                    - field: dateOfBirth
                      code: validation.dateFormat
                      message: dateOfBirth must be ISO 8601 date format YYYY-MM-DD
            payoutMethodConflict:
              summary: validation.payoutMethodConflict — both destinationIdentifier
                and payoutMethodId supplied
              value:
                error:
                  code: validation.payoutMethodConflict
                  message: Supply exactly one of destinationIdentifier or payoutMethodId.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
            paginationCursorInvalid:
              summary: pagination.cursorInvalid
              value:
                error:
                  code: pagination.cursorInvalid
                  message: The pagination cursor is unparseable or from a different
                    endpoint.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
    Unauthorized:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            tokenExpired:
              summary: auth.tokenExpired
              value:
                error:
                  code: auth.tokenExpired
                  message: The bearer token has expired.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    remediationHint: token_refresh
            assertionSignatureInvalid:
              summary: device.assertionSignatureInvalid (only at /transfers/{id}/confirm)
              value:
                error:
                  code: device.assertionSignatureInvalid
                  message: Device assertion signature does not verify against the
                    registered public key.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    remediationHint: restart_confirmation
    Forbidden:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            customerStatusBlocking:
              summary: customer.statusBlocking — customer in BLOCKED or CLOSED
              value:
                error:
                  code: customer.statusBlocking
                  message: Customer status does not permit this operation.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    currentStatus: BLOCKED
                    remediationHint: contact_support
            kycStatusInsufficient:
              summary: kyc.statusInsufficient
              value:
                error:
                  code: kyc.statusInsufficient
                  message: KYC must be completed before this operation.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    remediationHint: complete_kyc
            beneficiaryStateBlocking:
              summary: beneficiary.stateBlocking
              value:
                error:
                  code: beneficiary.stateBlocking
                  message: The selected beneficiary cannot be used.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    beneficiaryId: BEN-01HX9F2J7K3M5N7P9Q1R3T5V7W
                    currentState: BLOCKED
                    remediationHint: select_different_beneficiary
    NotFound:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            transferNotFound:
              summary: transfer.notFound
              value:
                error:
                  code: transfer.notFound
                  message: Transfer not found.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
            beneficiaryNotFound:
              summary: beneficiary.notFound
              value:
                error:
                  code: beneficiary.notFound
                  message: Beneficiary not found.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
    Conflict:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            terminalState:
              summary: transfer.terminalState
              value:
                error:
                  code: transfer.terminalState
                  message: Transfer is in a terminal state and cannot be modified.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
            cancellationInProgress:
              summary: transfer.cancellationInProgress
              value:
                error:
                  code: transfer.cancellationInProgress
                  message: A prior cancellation is still being coordinated with the
                    network.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    remediationHint: retry_later
            idempotencyKeyConflict:
              summary: idempotency.keyConflict
              value:
                error:
                  code: idempotency.keyConflict
                  message: The idempotency key was already used with a different request
                    body.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
    Gone:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            quoteExpiredGone:
              summary: quote.expired (at /disclosure)
              value:
                error:
                  code: quote.expired
                  message: Quote has expired.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    quoteId: Q-01HXFP6W7X9Z1B3D5F7H9J1L3N5
                    quoteExpiredAt: 2026-05-14 11:01:01+00:00
                    remediationHint: retry_later
    PreconditionFailed:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            deviceNotRegistered:
              summary: device.notRegistered
              value:
                error:
                  code: device.notRegistered
                  message: No active device registration for this customer.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    remediationHint: register_device
    UnsupportedMediaType:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            contentTypeUnsupported:
              summary: validation.contentTypeUnsupported
              value:
                error:
                  code: validation.contentTypeUnsupported
                  message: Content-Type must be application/json; charset=utf-8.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
    UnprocessableEntity:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            quoteExpired:
              summary: quote.expired (at /accept)
              value:
                error:
                  code: quote.expired
                  message: Quote has expired.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    quoteId: Q-01HXFP6W7X9Z1B3D5F7H9J1L3N5
                    quoteExpiredAt: 2026-05-14 11:01:01+00:00
                    remediationHint: retry_later
            envelopeBreach:
              summary: quote.envelopeBreach
              value:
                error:
                  code: quote.envelopeBreach
                  message: Pricing envelope re-check failed at acceptance time.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    remediationHint: retry_later
    TooManyRequests:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
        Retry-After:
          $ref: '#/components/headers/RetryAfterHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            rateLimited:
              summary: rate.limited
              value:
                error:
                  code: rate.limited
                  message: Rate limit exceeded. Retry after the indicated interval.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    remediationHint: rate_limit
            assertionLockout:
              summary: device.assertionLockout
              value:
                error:
                  code: device.assertionLockout
                  message: Device-assertion verification attempts exceeded threshold.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    retryAfterSeconds: 900
                    remediationHint: contact_support
    InternalServerError:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            internalError:
              summary: internal.error
              value:
                error:
                  code: internal.error
                  message: An internal error occurred. Please retry.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    remediationHint: server_unexpected
    BadGateway:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            fundingUpstreamUnavailable:
              summary: funding.upstreamUnavailable
              value:
                error:
                  code: funding.upstreamUnavailable
                  message: Funding provider upstream is unavailable.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
                  details:
                    remediationHint: upstream_retry
    ServiceUnavailable:
      headers:
        X-Correlation-Id:
          $ref: '#/components/headers/XCorrelationIdResponseHeader'
        Retry-After:
          $ref: '#/components/headers/RetryAfterHeader'
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          examples:
            internalUnavailable:
              summary: internal.unavailable
              value:
                error:
                  code: internal.unavailable
                  message: Service is temporarily unavailable. Please retry.
                  correlationId: c3f1a8b2-4d6e-4f0a-9c1b-2e8d7a6b5c4d
paths:
  /v1/core/profile:
    post:
      operationId: submitProfile
      tags:
      - Profile
      summary: Submit customer profile (identity-attribute capture).
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - $ref: '#/components/parameters/XIdempotencyKeyHeader'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/ProfileSubmitRequest'
            example:
              firstName: Aicha
              lastName: El Amrani
              middleNames:
              - Fatima
              dateOfBirth: '1990-03-15'
              nationality: MAR
              residenceCountry: ESP
              residenceAddress:
                addressLine1: Calle de Alcalá 42
                addressLine2: 3º A
                city: Madrid
                region: Madrid
                postalCode: '28014'
                country: ESP
              gender: FEMALE
              placeOfBirth:
                city: Casablanca
                country: MAR
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ProfileSubmitResponse'
              example:
                status: PENDING
                kycRequired: true
                nextStep: COMPLETE_KYC_CAPTURE
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '409':
          $ref: '#/components/responses/Conflict'
        '415':
          $ref: '#/components/responses/UnsupportedMediaType'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
    get:
      operationId: readProfile
      tags:
      - Profile
      summary: Read authenticated customer's profile, status, KYC state, identifiers.
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ProfileReadResponse'
              example:
                subscriptionId: SUB-01HX9F2J7K3M5N7P9Q1R3T5V7W
                status: VALID
                statusOperationalHint: null
                kycStatus: COMPLETED
                transactability: true
                customerActionExpected: false
                profile:
                  firstName: Aicha
                  lastName: El Amrani
                  middleNames:
                  - Fatima
                  dateOfBirth: '1990-03-15'
                  nationality: MAR
                  residenceCountry: ESP
                  residenceAddress:
                    addressLine1: Calle de Alcalá 42
                    addressLine2: 3º A
                    city: Madrid
                    region: Madrid
                    postalCode: '28014'
                    country: ESP
                  gender: FEMALE
                  placeOfBirth:
                    city: Casablanca
                    country: MAR
                identifiers:
                - identifierId: ID-01HX9F2J7K3M5N7P9Q1R3T5V7W
                  identifierType: EMAIL
                  identifierMasked: a****@example.com
                  verifiedAt: 2025-11-08 14:22:43+00:00
                  canRemove: true
                - identifierId: ID-01HX9F2J7K3M5N7P9Q1R3T5V7X
                  identifierType: PHONE
                  identifierMasked: +34******5678
                  verifiedAt: 2026-02-15 09:11:02+00:00
                  canRemove: true
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/kyc-sessions:
    post:
      operationId: createKycSession
      tags:
      - KYC
      summary: Initiate principal-served KYC capture session.
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - $ref: '#/components/parameters/XIdempotencyKeyHeader'
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/KycSessionCreateResponse'
              example:
                kycSessionId: KS-01HX9F2J7K3M5N7P9Q1R3T5V7W
                webviewUrl: https://kyc.eu.yescash.example/session/abc123def456ghi789jkl012mno345pqr
                expiresAt: 2026-05-12 14:35:12+00:00
                closureCallback:
                  scheme: yescash-partner
                  messageOrigin: https://kyc.eu.yescash.example
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/kyc-sessions/{kycSessionId}:
    get:
      operationId: readKycSession
      tags:
      - KYC
      summary: Read KYC session lifecycle state.
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/KycSessionIdPathParam'
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/KycSessionReadResponse'
              example:
                kycSessionId: KS-01HX9F2J7K3M5N7P9Q1R3T5V7W
                sessionState: CLOSED
                openedAt: 2026-05-11 13:32:18+00:00
                closedAt: 2026-05-11 13:48:42+00:00
                expiresAt: 2026-05-12 13:32:18+00:00
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          $ref: '#/components/responses/NotFound'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/quotes:
    post:
      operationId: createQuote
      tags:
      - Quotes
      summary: Create a partner-issued signed quote (re-presented to principal).
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - $ref: '#/components/parameters/XIdempotencyKeyHeader'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/QuoteCreateRequest'
            example:
              originAmount: '100.000000'
              originCurrency: EUR
              destinationCurrency: MAD
              beneficiaryId: BEN-01HXAJ9P0Q3R5T7V9X1Z3B5D7F
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/QuoteResponse'
              example:
                quoteId: Q-01HXFP6W7X9Z1B3D5F7H9J1L3N5
                originAmount: '100.000000'
                originCurrency: EUR
                destinationAmount: '1053.000000'
                destinationCurrency: MAD
                fxRate: '10.530000'
                principalFee: '1.500000'
                partnerFee: '0.500000'
                totalCustomerCost: '102.000000'
                totalCustomerCostCurrency: EUR
                quoteValidUntil: 2026-05-14 11:01:01+00:00
                quoteSignature: eyJ...<truncated>...
                quoteStatus: active
                corridor:
                  originCountry: ESP
                  destinationCountry: MAR
                  payoutMethod: bank_account
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '409':
          $ref: '#/components/responses/Conflict'
        '415':
          $ref: '#/components/responses/UnsupportedMediaType'
        '422':
          $ref: '#/components/responses/UnprocessableEntity'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '502':
          $ref: '#/components/responses/BadGateway'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/quotes/{quoteId}:
    get:
      operationId: getQuote
      tags:
      - Quotes
      summary: Fetch a signed quote by id.
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/QuoteIdPathParam'
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/QuoteResponse'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          $ref: '#/components/responses/NotFound'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/quotes/{quoteId}/disclosure:
    get:
      operationId: getQuoteDisclosure
      tags:
      - Quotes
      summary: Fetch regulator-aligned disclosure for a quote.
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/QuoteIdPathParam'
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - $ref: '#/components/parameters/AcceptLanguageHeader'
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
            Cache-Control:
              schema:
                type: string
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/DisclosureResponse'
              example:
                disclosureToken: DT-01HX9F2J7K3M5N7P9Q1R3T5V7W
                disclosureVersion: EU-ES-2026.04
                disclosureLanguage: es-ES
                disclosureText: 'INFORMACIÓN PRECONTRACTUAL — REMESA INTERNACIONAL


                  Usted está a punto de enviar 100,00 EUR a Marruecos.

                  ...'
                regulatoryAnchors:
                - PSD2_ARTICLE_44
                - PSD2_ARTICLE_45
                - RD_19_2018_TRANSPOSITION
                totalConsumerCost: '102.000000'
                sendAmount: '100.000000'
                sendCurrency: EUR
                receiveAmount: '1053.000000'
                receiveCurrency: MAD
                fxRate: '10.530000'
                issuedAt: 2026-05-14 11:00:10+00:00
                expiresAt: 2026-05-14 11:30:10+00:00
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          $ref: '#/components/responses/NotFound'
        '409':
          $ref: '#/components/responses/Conflict'
        '410':
          $ref: '#/components/responses/Gone'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/quotes/{quoteId}/accept:
    post:
      operationId: acceptQuote
      tags:
      - Quotes
      summary: Accept a quote (pricing commitment; creates transfer at registered).
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/QuoteIdPathParam'
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - $ref: '#/components/parameters/XIdempotencyKeyHeader'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/QuoteAcceptRequest'
            example:
              disclosureToken: DT-01HXBL2S3T5V7X9Z1A3C5E7G9I
              purposeOfTransfer: FAMILY_SUPPORT
      responses:
        '201':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
            Location:
              $ref: '#/components/headers/LocationHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/QuoteAcceptResponse'
              example:
                transferId: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
                transferStatus: registered
                quoteId: Q-01HXBK0R1S4U6V8X0Z2A4C6E8G
                acceptedAt: 2026-05-12 15:00:25+00:00
                nextStep: TRANSFER_CONFIRMATION_REQUIRED
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          $ref: '#/components/responses/NotFound'
        '409':
          $ref: '#/components/responses/Conflict'
        '412':
          $ref: '#/components/responses/PreconditionFailed'
        '415':
          $ref: '#/components/responses/UnsupportedMediaType'
        '422':
          $ref: '#/components/responses/UnprocessableEntity'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/beneficiaries:
    get:
      operationId: listBeneficiaries
      tags:
      - Beneficiaries
      summary: List the customer's beneficiaries.
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - name: states
        in: query
        required: false
        schema:
          type: string
        example: VALID,MONITORED
      - name: cursor
        in: query
        required: false
        schema:
          type: string
      - name: limit
        in: query
        required: false
        schema:
          type: integer
          minimum: 1
          maximum: 200
          default: 50
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/BeneficiaryListResponse'
              example:
                items:
                - beneficiaryId: BEN-01HX9F2J7K3M5N7P9Q1R3T5V7W
                  firstName: Fatima
                  lastName: El Amrani
                  state: VALID
                  createdAt: 2026-05-08 11:24:31+00:00
                  lastUsedAt: 2026-05-11 13:02:17+00:00
                  payoutMethodCount: 2
                - beneficiaryId: BEN-01HX9F2J7K3M5N7P9Q1R3T5V8X
                  firstName: Ahmed
                  lastName: Benali
                  state: VALID
                  createdAt: 2026-04-22 09:15:00+00:00
                  lastUsedAt: null
                  payoutMethodCount: 0
                nextCursor: null
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
    post:
      operationId: createBeneficiary
      tags:
      - Beneficiaries
      summary: Create a beneficiary (triggers asynchronous screening).
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - $ref: '#/components/parameters/XIdempotencyKeyHeader'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/BeneficiaryCreateRequest'
            example:
              firstName: Fatima
              lastName: El Amrani
              dateOfBirth: '1985-03-12'
              address:
                addressLine1: 12 Rue de la Liberté
                city: Casablanca
                postalCode: '20000'
                country: MAR
              nationality: MA
              countryOfResidence: MA
              relationshipToCustomer: PARENT
      responses:
        '202':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
            Location:
              $ref: '#/components/headers/LocationHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/BeneficiaryCreateResponse'
              example:
                beneficiaryId: BEN-01HX9F2J7K3M5N7P9Q1R3T5V7W
                state: PENDING
                createdAt: 2026-05-08 11:24:31+00:00
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '409':
          $ref: '#/components/responses/Conflict'
        '415':
          $ref: '#/components/responses/UnsupportedMediaType'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/beneficiaries/{beneficiaryId}:
    get:
      operationId: getBeneficiary
      tags:
      - Beneficiaries
      summary: Read beneficiary detail (identity attributes, state, payout methods).
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/BeneficiaryIdPathParam'
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/BeneficiaryDetailResponse'
              example:
                beneficiaryId: BEN-01HX9F2J7K3M5N7P9Q1R3T5V7W
                firstName: Fatima
                lastName: El Amrani
                dateOfBirth: '1985-03-12'
                address:
                  addressLine1: 12 Rue de la Liberté
                  city: Casablanca
                  postalCode: '20000'
                  country: MAR
                nationality: MA
                countryOfResidence: MA
                relationshipToCustomer: PARENT
                state: VALID
                createdAt: 2026-05-08 11:24:31+00:00
                stateChangedAt: 2026-05-08 11:24:34+00:00
                lastUsedAt: 2026-05-11 13:02:17+00:00
                customerActionExpected: null
                payoutMethods:
                - payoutMethodId: PM-01HX9F2J7K3M5N7P9Q1R3T5V7W
                  methodType: BANK_TRANSFER
                  corridor: ES-MA
                  destinationIdentifierMasked: '****1234'
                  addedAt: 2026-05-09 10:32:18+00:00
                  archived: false
                - payoutMethodId: PM-01HX9F2J7K3M5N7P9Q1R3T5V8X
                  methodType: CASH_PICKUP
                  corridor: ES-MA
                  destinationIdentifierMasked: '****5678'
                  addedAt: 2026-05-10 14:21:09+00:00
                  archived: false
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          $ref: '#/components/responses/NotFound'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/beneficiaries/{beneficiaryId}/archive:
    post:
      operationId: archiveBeneficiary
      tags:
      - Beneficiaries
      summary: Archive a beneficiary (one-way customer-initiated).
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/BeneficiaryIdPathParam'
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - $ref: '#/components/parameters/XIdempotencyKeyHeader'
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/BeneficiaryArchiveResponse'
              example:
                beneficiaryId: BEN-01HX9F2J7K3M5N7P9Q1R3T5V7W
                state: ARCHIVED
                archivedAt: 2026-05-12 10:15:00+00:00
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          $ref: '#/components/responses/NotFound'
        '409':
          $ref: '#/components/responses/Conflict'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/transfers:
    get:
      operationId: listTransfers
      tags:
      - Transfers
      summary: List the customer's transfers (summary projection).
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - name: states
        in: query
        required: false
        schema:
          type: string
        example: funded,topay,reqpay
      - name: createdSince
        in: query
        required: false
        schema:
          type: string
          format: date-time
        example: 2026-05-01 00:00:00+00:00
      - name: cursor
        in: query
        required: false
        schema:
          type: string
      - name: limit
        in: query
        required: false
        schema:
          type: integer
          minimum: 1
          maximum: 200
          default: 50
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TransferListResponse'
              example:
                items:
                - transferId: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
                  transferStatus: paid
                  transferStateChangedAt: 2026-05-11 18:42:55+00:00
                  createdAt: 2026-05-11 15:00:25+00:00
                  originAmount: '100.000000'
                  originCurrency: EUR
                  destinationAmount: '1053.000000'
                  destinationCurrency: MAD
                  beneficiaryId: BEN-01HXAJ9P0Q3R5T7V9X1Z3B5D7F
                - transferId: TRF-01HXDN4U5V7X9Z1B3C5E7G9I1K
                  transferStatus: topay
                  transferStateChangedAt: 2026-05-12 11:22:00+00:00
                  createdAt: 2026-05-12 11:00:00+00:00
                  originAmount: '250.000000'
                  originCurrency: EUR
                  destinationAmount: '2632.500000'
                  destinationCurrency: MAD
                  beneficiaryId: BEN-01HXAJ9P0Q3R5T7V9X1Z3B5D7F
                nextCursor: null
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/transfers/{transferId}:
    get:
      operationId: getTransfer
      tags:
      - Transfers
      summary: Read transfer detail (state-conditional fields; re-issues confirmationChallenge).
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/TransferIdPathParam'
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TransferDetailResponse'
              examples:
                validated:
                  summary: transferStatus = validated (fresh confirmationChallenge
                    issued)
                  value:
                    transferId: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
                    transferStatus: validated
                    transferStateChangedAt: 2026-05-11 15:11:30+00:00
                    originAmount: '100.000000'
                    originCurrency: EUR
                    destinationAmount: '1053.000000'
                    destinationCurrency: MAD
                    fxRate: '10.530000'
                    principalFee: '1.500000'
                    partnerFee: '0.500000'
                    totalCustomerCost: '102.000000'
                    totalCustomerCostCurrency: EUR
                    beneficiaryId: BEN-01HXAJ9P0Q3R5T7V9X1Z3B5D7F
                    payoutMethod:
                      payoutMethodId: PM-01HX9F2J7K3M5N7P9Q1R3T5V7W
                      methodType: BANK_TRANSFER
                      corridor: ES-MA
                      destinationIdentifierMasked: '****1332'
                      archived: false
                    purposeOfTransfer: FAMILY_SUPPORT
                    quoteId: Q-01HXBK0R1S4U6V8X0Z2A4C6E8G
                    createdAt: 2026-05-11 15:11:22+00:00
                    submittedAt: 2026-05-11 15:11:25+00:00
                    confirmedAt: null
                    transferExpiresAt: 2026-05-11 17:11:22+00:00
                    nextStep: AWAIT_DEVICE_AUTHENTICATION
                    customerActionExpected: CONFIRM_TRANSFER
                    confirmationChallenge: Ch7L9mN2pQ4rS6tU8vW0xY1zA3bC5dE7fG9hI1jK3l
                    confirmationChallengeExpiresAt: 2026-05-11 15:21:30+00:00
                    fundingSession: null
                    cancellation: null
                    refund: null
                    stateHistory:
                    - state: registered
                      transitionedAt: 2026-05-11 15:11:22+00:00
                      reasonCode: TRF_INITIATION_QUOTE_ACCEPTED
                    - state: validated
                      transitionedAt: 2026-05-11 15:11:30+00:00
                      reasonCode: TRF_CHECK_PASSED
                funding:
                  summary: transferStatus = funding (fundingSession populated)
                  value:
                    transferId: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
                    transferStatus: funding
                    transferStateChangedAt: 2026-05-11 15:12:15+00:00
                    originAmount: '100.000000'
                    originCurrency: EUR
                    destinationAmount: '1053.000000'
                    destinationCurrency: MAD
                    beneficiaryId: BEN-01HXAJ9P0Q3R5T7V9X1Z3B5D7F
                    quoteId: Q-01HXBK0R1S4U6V8X0Z2A4C6E8G
                    createdAt: 2026-05-11 15:11:22+00:00
                    submittedAt: 2026-05-11 15:11:25+00:00
                    confirmedAt: 2026-05-11 15:12:15+00:00
                    transferExpiresAt: 2026-05-11 17:11:22+00:00
                    nextStep: OPEN_FUNDING_WEBVIEW
                    customerActionExpected: OPEN_FUNDING_WEBVIEW
                    confirmationChallenge: null
                    confirmationChallengeExpiresAt: null
                    fundingSession:
                      fundingSessionId: FND-01HXKT1B2C4D6F8H0J2L4N6P8R0
                      fundingWebviewUrl: https://funding.eu.yescash.example/sessions/FND-01HXKT1B2C4D6F8H0J2L4N6P8R0
                      expiresAt: 2026-05-11 15:42:15+00:00
                    cancellation: null
                    refund: null
                canceledWithRefund:
                  summary: transferStatus = canceled (refund initiated)
                  value:
                    transferId: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
                    transferStatus: canceled
                    transferStateChangedAt: 2026-05-11 15:35:22+00:00
                    originAmount: '100.000000'
                    originCurrency: EUR
                    destinationAmount: '1053.000000'
                    destinationCurrency: MAD
                    beneficiaryId: BEN-01HXAJ9P0Q3R5T7V9X1Z3B5D7F
                    quoteId: Q-01HXBK0R1S4U6V8X0Z2A4C6E8G
                    createdAt: 2026-05-11 15:11:22+00:00
                    submittedAt: 2026-05-11 15:11:25+00:00
                    confirmedAt: 2026-05-11 15:12:15+00:00
                    nextStep: WAIT_REFUND
                    customerActionExpected: WAIT_REFUND
                    confirmationChallenge: null
                    confirmationChallengeExpiresAt: null
                    fundingSession: null
                    cancellation:
                      cancellationOutcome: CANCELED_PRE_NETWORK
                      cancellationReason: CHANGED_MIND
                      cancelRequestedAt: 2026-05-11 15:35:22+00:00
                      canceledAt: 2026-05-11 15:35:22+00:00
                      networkCancellationExpectedBy: null
                    refund:
                      refundStatus: REFUND_PENDING
                      estimatedRefundCompletionBy: 2026-05-11 15:40:22+00:00
                      refundMethod: ORIGINAL_PAYMENT_METHOD
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          $ref: '#/components/responses/NotFound'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/transfers/{transferId}/submit:
    post:
      operationId: submitTransfer
      tags:
      - Transfers
      summary: Submit recipient + destination + purpose; triggers fast-check.
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/TransferIdPathParam'
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - $ref: '#/components/parameters/XIdempotencyKeyHeader'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/TransferSubmitRequest'
            example:
              beneficiaryId: BEN-01HXAJ9P0Q3R5T7V9X1Z3B5D7F
              payoutMethod:
                methodType: BANK_TRANSFER
                destinationIdentifier: ES9121000418450200051332
                payoutMethodId: null
              purposeOfTransfer: FAMILY_SUPPORT
      responses:
        '202':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
            Location:
              $ref: '#/components/headers/LocationHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TransferSubmitResponse'
              example:
                transferId: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
                transferStatus: registered
                beneficiaryId: BEN-01HXAJ9P0Q3R5T7V9X1Z3B5D7F
                payoutMethod:
                  payoutMethodId: PM-01HX9F2J7K3M5N7P9Q1R3T5V7W
                  methodType: BANK_TRANSFER
                  corridor: ES-MA
                  destinationIdentifierMasked: '****1332'
                  archived: false
                purposeOfTransfer: FAMILY_SUPPORT
                submittedAt: 2026-05-11 15:11:25+00:00
                fastCheckExpectedBy: 2026-05-11 15:11:30+00:00
                nextStep: AWAIT_FAST_CHECK
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          $ref: '#/components/responses/NotFound'
        '409':
          $ref: '#/components/responses/Conflict'
        '410':
          $ref: '#/components/responses/Gone'
        '415':
          $ref: '#/components/responses/UnsupportedMediaType'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/transfers/{transferId}/cancel:
    post:
      operationId: cancelTransfer
      tags:
      - Transfers
      summary: Cancel a transfer (consumer-protection floor; cancellable until paid).
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/TransferIdPathParam'
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - $ref: '#/components/parameters/XIdempotencyKeyHeader'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/TransferCancelRequest'
            example:
              cancellationReason: CHANGED_MIND
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TransferCancelResponse'
              example:
                transferId: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
                transferStatus: aborted
                cancellationOutcome: ABORTED_PRE_FUNDING
                canceledAt: 2026-05-11 15:35:22+00:00
                nextStep: null
                customerActionExpected: NONE
                refund: null
        '202':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TransferCancelResponse'
              examples:
                fundedCanceled:
                  summary: funded state — synchronous canceled + async refund
                  value:
                    transferId: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
                    transferStatus: canceled
                    cancellationOutcome: CANCELED_PRE_NETWORK
                    canceledAt: 2026-05-11 15:35:22+00:00
                    nextStep: WAIT_REFUND
                    customerActionExpected: WAIT_REFUND
                    refund:
                      refundStatus: REFUND_INITIATED
                      estimatedRefundCompletionBy: 2026-05-11 15:40:22+00:00
                      refundMethod: ORIGINAL_PAYMENT_METHOD
                networkPending:
                  summary: topay/reqpay state — network-coordination pending
                  value:
                    transferId: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
                    transferStatus: topay
                    cancellationOutcome: NETWORK_CANCELLATION_PENDING
                    canceledAt: null
                    nextStep: WAIT
                    customerActionExpected: WAIT
                    networkCancellationExpectedBy: 2026-05-11 15:56:22+00:00
                    refund: null
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          $ref: '#/components/responses/NotFound'
        '409':
          $ref: '#/components/responses/Conflict'
        '415':
          $ref: '#/components/responses/UnsupportedMediaType'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '502':
          $ref: '#/components/responses/BadGateway'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
  /v1/core/transfers/{transferId}/confirm:
    post:
      operationId: confirmTransfer
      tags:
      - Transfers
      summary: Device-bound release-funds confirmation; promotes validated to funding.
      security:
      - apimSubscriptionKey: []
        bearerAuth: []
      parameters:
      - $ref: '#/components/parameters/TransferIdPathParam'
      - $ref: '#/components/parameters/XCorrelationIdHeader'
      - $ref: '#/components/parameters/XIdempotencyKeyHeader'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/DeviceAssertion'
            example:
              deviceAssertion: eyJhbGciOiJSUzI1NiIsImtpZCI6ImRldmljZS1rZXktMjAyNi0wNS0xMVQxNC01OFoiLCJ0eXAiOiJKV1QifQ.eyJ0cmFuc2Zlcl9pZCI6IlRSRi0wMUhYQ00zVDRVNlc4WTBBMkI0RDZGOEgwSiIsImFtb3VudCI6IjEwMC4wMCIsImN1cnJlbmN5IjoiRVVSIiwiYmVuZWZpY2lhcnlfaWQiOiJCRU4tMDFIWEFKOVAwUTNSNVQ3VjlYMVozQjVEN0YiLCJkZXZpY2VfaWQiOiJERVYtMDFIWDlGMko3SzNNNU43UDlRMVIzVDVWN1ciLCJub25jZSI6Ii4uLiIsImNoYWxsZW5nZSI6IkNoN0w5bU4ycFE0clM2dFU4dlcweFkxekEzYkM1ZEU3Zkc5aEkxaksybCIsImlhdCI6MTcxNTYwODgyMn0.signature_bytes_omitted
      responses:
        '200':
          headers:
            X-Correlation-Id:
              $ref: '#/components/headers/XCorrelationIdResponseHeader'
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TransferConfirmResponse'
              example:
                transferId: TRF-01HXCM3T4U6W8Y0A2B4D6F8H0J
                transferStatus: funding
                confirmedAt: 2026-05-11 15:12:15+00:00
                nextStep: OPEN_FUNDING_WEBVIEW
                fundingSession:
                  fundingSessionId: FND-01HXKT1B2C4D6F8H0J2L4N6P8R0
                  fundingWebviewUrl: https://funding.eu.yescash.example/sessions/FND-01HXKT1B2C4D6F8H0J2L4N6P8R0
                  expiresAt: 2026-05-11 15:42:15+00:00
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          $ref: '#/components/responses/NotFound'
        '409':
          $ref: '#/components/responses/Conflict'
        '412':
          $ref: '#/components/responses/PreconditionFailed'
        '415':
          $ref: '#/components/responses/UnsupportedMediaType'
        '422':
          $ref: '#/components/responses/UnprocessableEntity'
        '429':
          $ref: '#/components/responses/TooManyRequests'
        '500':
          $ref: '#/components/responses/InternalServerError'
        '503':
          $ref: '#/components/responses/ServiceUnavailable'
