{
  "openapi": "3.0.3",
  "info": {
    "title": "DCC rate service API",
    "description": "This is an API reference for the DCC (Dynamic Currency Conversion) rate service.",
    "version": "1.0.0"
  },
  "servers": [
    {
      "url": "https://api-services.pxp.io/api/v1",
      "description": "Production environment"
    },
    {
      "url": "https://api-services.test.pxp.io/api/v1",
      "description": "Sandbox environment"
    }
  ],
  "paths": {
    "/dcc/rate": {
      "post": {
        "x-hideReplay": true,
        "operationId": "get-dcc-rate",
        "summary": "Get DCC rate",
        "description": "Retrieve the Dynamic Currency Conversion (DCC) rate for a transaction from various providers.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/DccRateRequest"
              },
              "examples": {
                "elavon-example": {
                  "summary": "Elavon",
                  "description": "Example request for Elavon provider.",
                  "value": {
                    "merchant": "MERCHANT-001",
                    "site": "SITE-001",
                    "exchangeRateProvider": "Elavon",
                    "securityLevel": {
                      "primaryAccountNumber": "{primaryAccountNumber}"
                    },
                    "transactionMethod": {
                      "entryMode": "Instore",
                      "intent": "Authorisation"
                    },
                    "pointOfInteraction": {
                      "entryType": "ChipAndPin",
                      "merchantPointOfSaleId": "POS-001"
                    },
                    "amounts": {
                      "localTransaction": 100,
                      "localCurrencyCode": "USD",
                      "cardHolderCurrencyCode": "EUR"
                    }
                  }
                },
                "fexco-example": {
                  "summary": "Fexco",
                  "description": "Example request for Fexco provider.",
                  "value": {
                    "merchant": "MERCHANT-001",
                    "site": "SITE-001",
                    "exchangeRateProvider": "Fexco",
                    "securityLevel": {
                      "primaryAccountNumber": "{primaryAccountNumber}"
                    },
                    "transactionMethod": {
                      "entryMode": "Instore",
                      "intent": "Authorisation"
                    },
                    "pointOfInteraction": {
                      "entryType": "ChipAndPin",
                      "merchantPointOfSaleId": "POS-001"
                    },
                    "amounts": {
                      "localTransaction": 100,
                      "localCurrencyCode": "USD",
                      "cardHolderCurrencyCode": "EUR"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Success",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/DccRateResponse"
                },
                "examples": {
                  "elavon-response": {
                    "summary": "Elavon",
                    "description": "Example response from Elavon provider",
                    "value": {
                      "state": "Available",
                      "amounts": {
                        "local": {
                          "transaction": 100,
                          "currencyCode": "USD"
                        },
                        "cardholder": {
                          "transaction": 85.5,
                          "currencyCode": "EUR"
                        }
                      },
                      "exchangeRate": {
                        "rate": 0.855,
                        "exponent": 3,
                        "markUpPercentage": 3.5,
                        "commissionRate": 0.025,
                        "margin": 2.1
                      },
                      "messaging": {
                        "markUpMessage": "Competitive exchange rate with 3.5% markup",
                        "disclaimer": "Exchange rate includes markup and may vary"
                      },
                      "providerResponse": {
                        "provider": "Elavon",
                        "referenceId": "REF123456789",
                        "terminalId": "TERM001"
                      }
                    }
                  },
                  "fexco-response": {
                    "summary": "Fexco",
                    "description": "Example response from Fexco provider",
                    "value": {
                      "state": "Available",
                      "amounts": {
                        "local": {
                          "transaction": 100,
                          "currencyCode": "USD"
                        },
                        "cardholder": {
                          "transaction": 86.2,
                          "currencyCode": "EUR"
                        }
                      },
                      "exchangeRate": {
                        "rate": 0.862,
                        "exponent": 3,
                        "markUpPercentage": 3.2,
                        "commissionRate": 0.022,
                        "margin": 1.8
                      },
                      "messaging": {
                        "markUpMessage": "Fexco competitive rate with 3.2% markup",
                        "disclaimer": "Fexco rate subject to market conditions"
                      },
                      "providerResponse": {
                        "provider": "Fexco",
                        "referenceId": "FX987654321",
                        "terminalId": "TERM001"
                      }
                    }
                  },
                  "dcc-not-available": {
                    "summary": "Not available",
                    "description": "Example response when DCC service is not available",
                    "value": {
                      "state": "NotAvailable",
                      "amounts": {
                        "local": {
                          "transaction": 100,
                          "currencyCode": "USD"
                        },
                        "cardholder": {
                          "transaction": 0,
                          "currencyCode": "EUR"
                        }
                      },
                      "exchangeRate": {
                        "rate": 0,
                        "exponent": 0,
                        "markUpPercentage": 0,
                        "commissionRate": 0,
                        "margin": 0
                      },
                      "messaging": {
                        "markUpMessage": "",
                        "disclaimer": "DCC service not available for this transaction"
                      },
                      "providerResponse": {
                        "provider": "Elavon",
                        "referenceId": "",
                        "terminalId": ""
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad request",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorised",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "CurrencyCode": {
        "type": "string",
        "description": "Currency code in ISO 4217 format.",
        "example": "USD",
        "minLength": 3,
        "maxLength": 3,
        "pattern": "^[A-Z]{3}$"
      },
      "BaseAmount": {
        "type": "object",
        "required": [
          "localTransaction",
          "localCurrencyCode"
        ],
        "properties": {
          "localCurrencyCode": {
            "$ref": "#/components/schemas/CurrencyCode"
          },
          "localTransaction": {
            "type": "number",
            "description": "The transaction amount in the local currency.",
            "example": 100,
            "minimum": 0.01
          }
        }
      },
      "BaseProviderResponse": {
        "type": "object",
        "description": "Base structure for provider responses.",
        "required": [
          "provider"
        ],
        "properties": {
          "provider": {
            "type": "string",
            "description": "The name of the provider."
          }
        }
      },
      "RequestAmounts": {
        "allOf": [
          {
            "$ref": "#/components/schemas/BaseAmount"
          },
          {
            "type": "object",
            "properties": {
              "cardHolderCurrencyCode": {
                "$ref": "#/components/schemas/CurrencyCode",
                "description": "The cardholder's currency, in ISO 4217 format."
              }
            }
          }
        ]
      },
      "ResponseAmounts": {
        "type": "object",
        "description": "Details about the amounts.",
        "required": [
          "local",
          "cardholder"
        ],
        "properties": {
          "local": {
            "type": "object",
            "required": [
              "transaction",
              "currencyCode"
            ],
            "properties": {
              "transaction": {
                "type": "number",
                "description": "The transaction amount in the local currency.",
                "example": 100
              },
              "currencyCode": {
                "$ref": "#/components/schemas/CurrencyCode"
              }
            }
          },
          "cardholder": {
            "type": "object",
            "required": [
              "transaction",
              "currencyCode"
            ],
            "properties": {
              "transaction": {
                "type": "number",
                "description": "The transaction amount in the cardholder's currency.",
                "example": 85.5
              },
              "currencyCode": {
                "$ref": "#/components/schemas/CurrencyCode"
              }
            }
          }
        }
      },
      "DccRateRequest": {
        "type": "object",
        "required": [
          "merchant",
          "site",
          "exchangeRateProvider",
          "securityLevel",
          "transactionMethod",
          "amounts"
        ],
        "properties": {
          "merchant": {
            "type": "string",
            "description": "Your unique merchant identifier, as assigned by PXP.",
            "example": "MERCHANT-1",
            "maxLength": 20
          },
          "site": {
            "type": "string",
            "description": "Your unique site identifier, as assigned by PXP.",
            "example": "SITE-1",
            "maxLength": 20
          },
          "exchangeRateProvider": {
            "type": "string",
            "enum": [
              "Elavon",
              "Fexco"
            ],
            "description": "The exchange rate provider to use for the DCC rate calculation.",
            "example": "Elavon"
          },
          "securityLevel": {
            "$ref": "#/components/schemas/SecurityLevel"
          },
          "transactionMethod": {
            "$ref": "#/components/schemas/TransactionMethod"
          },
          "pointOfInteraction": {
            "$ref": "#/components/schemas/PointOfInteraction"
          },
          "amounts": {
            "$ref": "#/components/schemas/RequestAmounts"
          }
        }
      },
      "PointOfInteraction": {
        "type": "object",
        "description": "Details about the point of interaction. This object is optional for `Ecom` transactions.",
        "properties": {
          "entryType": {
            "type": "string",
            "enum": [
              "CardContactless",
              "ChipAndPin"
            ],
            "description": "The type of entry used to capture the card details.",
            "example": "ChipAndPin",
            "minLength": 1
          },
          "merchantPointOfSaleId": {
            "type": "string",
            "description": "The unique identifier for the merchant point of sale.",
            "example": "POS-001",
            "minLength": 1
          }
        }
      },
      "SecurityLevel": {
        "type": "object",
        "description": "Details about the security level of the transaction.",
        "required": [
          "primaryAccountNumber"
        ],
        "properties": {
          "primaryAccountNumber": {
            "type": "string",
            "description": "The primary account number.",
            "example": "{primaryAccountNumber}",
            "minLength": 1
          }
        }
      },
      "TransactionMethod": {
        "type": "object",
        "description": "Details about the transaction method.",
        "required": [
          "entryMode",
          "intent"
        ],
        "properties": {
          "entryMode": {
            "type": "string",
            "enum": [
              "Instore",
              "Ecom"
            ],
            "description": "The entry mode of the transaction."
          },
          "intent": {
            "type": "string",
            "enum": [
              "Purchase",
              "Authorisation",
              "EstimatedAuthorisation",
              "Capture",
              "FinalCapture",
              "Refund",
              "Reversal"
            ],
            "description": "The intent of the transaction."
          }
        }
      },
      "DccRateResponse": {
        "type": "object",
        "description": "The response body containing the DCC rate.",
        "required": [
          "state",
          "amounts",
          "exchangeRate",
          "messaging",
          "providerResponse"
        ],
        "properties": {
          "state": {
            "type": "string",
            "enum": [
              "Available",
              "NotAvailable",
              "CardEligible",
              "CardNotEligible",
              "Error"
            ],
            "description": "The state of the DCC rate request."
          },
          "amounts": {
            "$ref": "#/components/schemas/ResponseAmounts"
          },
          "exchangeRate": {
            "$ref": "#/components/schemas/ExchangeRate"
          },
          "messaging": {
            "$ref": "#/components/schemas/Messaging"
          },
          "providerResponse": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/ElavonProviderResponse"
              },
              {
                "$ref": "#/components/schemas/FexcoProviderResponse"
              }
            ]
          }
        }
      },
      "Messaging": {
        "type": "object",
        "description": "Details about the messaging of the DCC rate request.",
        "required": [
          "markUpMessage",
          "disclaimer"
        ],
        "properties": {
          "markUpMessage": {
            "type": "string",
            "description": "Message about the markup.",
            "example": "Competitive exchange rate with 3.5% markup"
          },
          "disclaimer": {
            "type": "string",
            "description": "Disclaimer text about the rate.",
            "example": "Exchange rate includes markup and may vary."
          }
        }
      },
      "ExchangeRate": {
        "type": "object",
        "description": "Details about the exchange rate.",
        "required": [
          "rate",
          "exponent",
          "markUpPercentage",
          "commissionRate",
          "margin"
        ],
        "properties": {
          "rate": {
            "type": "number",
            "description": "The foreign exchange rate.",
            "example": 0.855
          },
          "exponent": {
            "type": "integer",
            "description": "The exponent of the foreign exchange rate.",
            "example": 3
          },
          "markUpPercentage": {
            "type": "number",
            "description": "The markup percentage.",
            "example": 3
          },
          "commissionRate": {
            "type": "number",
            "description": "The commission rate applied.",
            "example": 0.025
          },
          "margin": {
            "type": "number",
            "description": "The margin applied.",
            "example": 2.1
          }
        }
      },
      "ElavonProviderResponse": {
        "type": "object",
        "description": "Details about the Elavon provider response.",
        "allOf": [
          {
            "$ref": "#/components/schemas/BaseProviderResponse"
          },
          {
            "type": "object",
            "required": [
              "referenceId",
              "terminalId"
            ],
            "properties": {
              "provider": {
                "type": "string",
                "description": "The name of the provider.",
                "example": "Elavon"
              },
              "referenceId": {
                "type": "string",
                "description": "The Elavon reference ID.",
                "example": "REF123456789"
              },
              "terminalId": {
                "type": "string",
                "description": "The terminal ID provided by Elavon.",
                "example": "TERM001"
              }
            }
          }
        ]
      },
      "FexcoProviderResponse": {
        "type": "object",
        "description": "Details about the Fexco provider response.",
        "allOf": [
          {
            "$ref": "#/components/schemas/BaseProviderResponse"
          },
          {
            "type": "object",
            "required": [
              "referenceId",
              "terminalId"
            ],
            "properties": {
              "provider": {
                "type": "string",
                "description": "The name of the provider.",
                "example": "Fexco"
              },
              "referenceId": {
                "type": "string",
                "description": "The reference ID provided by Fexco.",
                "example": "FX987654321"
              },
              "terminalId": {
                "type": "string",
                "description": "The terminal ID provided by Fexco.",
                "example": "TERM001"
              }
            }
          }
        ]
      },
      "ErrorResponse": {
        "type": "object",
        "description": "Details about the error response.",
        "required": [
          "error",
          "message"
        ],
        "properties": {
          "error": {
            "type": "string",
            "description": "The error code.",
            "example": "VALIDATION_ERROR"
          },
          "message": {
            "type": "string",
            "description": "The error message.",
            "example": "Either encryptedPayload or primaryAccountNumber must be provided in securityLevel"
          },
          "details": {
            "type": "string",
            "description": "Additional details about the error.",
            "example": "List [ \"Field 'merchant' is required\", \"Field 'localTransaction' must be greater than 0\" ]"
          }
        }
      }
    }
  }
}