Skip to main content

Quotations

A quotation locks an exchange rate, fees and the resulting amounts for a short window. Create one before building an order, then reference its id β€” an order that references an expired or already-used quotation fails before any money moves. See Orders for create_order.

create_quotation​

Locks a rate for a transfer corridor: a source currency, a destination country/currency/payout method, and the amount you want quoted.

Signature​

def create_quotation(self, request: CreateQuotationRequest) -> QuotationDetail:

Parameters​

NameTypeRequiredDescription
requestCreateQuotationRequestYesThe quote to build.

CreateQuotationRequest fields:

FieldTypeRequiredDescription
sourceQuotationSourceYesWhere the money comes from. Carries only currency β€” adding anything else is a 400.
source.currencystrYesNon-empty currency code, e.g. "USDR".
destinationQuotationDestinationYesWhere the money is going.
destination.countrystrYes2-character ISO alpha-2 country code, uppercase, e.g. "VE".
destination.currencystrYesNon-empty currency code, e.g. "VES".
destination.payout_methodQuotationPayoutMethodYesHow the recipient will be paid.
destination.payout_method.typePayoutMethodTypeYesPayoutMethodType.BANK_TRANSFER or PayoutMethodType.P2P_PHONE_TRANSFER.
quoteQuotationQuoteYesThe amount being quoted.
quote.modeQuoteModeYesQuoteMode.SEND_EXACT (the sender parts with exactly quote.amount) or QuoteMode.RECEIVE_EXACT (the recipient gets exactly quote.amount).
quote.amountstrYesDecimal string with up to 6 decimals, e.g. "56.00". Never a float.

Returns​

QuotationDetail:

FieldTypeDescription
idOptional[str]The quotation id. Pass it as quotation_id to create_order.
sourceOptional[QuotationSourceDetail]currency, decimals, gross_amount, net_amount β€” the source side, before and after fees.
destinationOptional[QuotationDestinationDetail]country (ISO-2) and payout_method.type β€” the corridor the quotation locked. The order's payment instructions must match payout_method.type, or create_order fails with B2B_QUOTATION_MISMATCH. Both are None only when the network could not attach a rate β€” do not build an order on that quotation.
targetOptional[QuotationTargetDetail]currency, decimals, amount β€” what the recipient side computes to.
exchange_rateOptional[ExchangeRate]value (decimal string), quoted_at, expires_at β€” the locked rate and its validity window.
feesOptional[QuotationFees]total_in_source_currency plus a breakdown list of FeeBreakdownItem (description, pricing_type, applied_to, value, currency).

Example​

from retorna_sdk import (
CreateQuotationRequest, QuotationSource, QuotationDestination,
QuotationPayoutMethod, QuotationQuote, QuoteMode, PayoutMethodType,
)

# client is the RetornaClient from the overview's RetornaClient.create(...)
quotation = client.create_quotation(CreateQuotationRequest(
source=QuotationSource(currency="USDR"),
destination=QuotationDestination(
country="VE", currency="VES",
payout_method=QuotationPayoutMethod(type=PayoutMethodType.BANK_TRANSFER)),
quote=QuotationQuote(mode=QuoteMode.SEND_EXACT, amount="56.00"),
))
print(quotation.id, quotation.exchange_rate.value, quotation.target.amount)
print(quotation.destination.payout_method.type) # "P2P_PHONE_TRANSFER" β†’ use bank_phone_account on the order

Errors​

  • B2B_RATE_NOT_FOUND β€” no active rate for this source/destination/payout-method corridor. Check get_routes first.
  • B2B_RATE_LIMITED β€” too many requests; retry with backoff.
  • B2B_UNAUTHORIZED β€” bad token or bad request signature.
  • ValueError β€” raised locally, before any request goes out, when request, source, destination or quote is None; when quote.mode or destination.payout_method.type is not a valid enum member; or when source.currency/destination.currency is empty, destination.country is not a 2-letter uppercase code, or quote.amount is not a decimal string.

Notes​

  • source carries only currency β€” no country or network. The DTO enforces this even where old documentation says otherwise.
  • The quotation expires quickly; do not cache one across requests you expect to take more than a few minutes.

API reference​

POST /quotations

get_quotation​

Re-fetches a previously created quotation by its id β€” useful to check whether it is still within its validity window before building an order from it.

Signature​

def get_quotation(self, quotation_id: str) -> QuotationDetail:

Parameters​

NameTypeRequiredDescription
quotation_idstrYesOpaque id, 1 to 100 characters β€” not necessarily a UUID.

Returns​

Same QuotationDetail as create_quotation β€” see the table above.

Example​

quotation = client.get_quotation(quotation.id)
print(quotation.id, quotation.exchange_rate.expires_at)

Errors​

  • B2B_QUOTATION_NOT_FOUND β€” the id does not exist, or does not belong to your company.
  • B2B_UNAUTHORIZED β€” bad token or bad request signature.
  • ValueError β€” raised locally when quotation_id is None or its length is outside 1..100 characters.

Notes​

  • Fetching a quotation does not extend or refresh it β€” expires_at is fixed at creation time.

API reference​

GET /quotations/{id}