Skip to content
FX-Port/Docs
GuidesAPI referenceChangelog
Get API keys
  • Introduction
  • Quickstart
  • Security
  • Authentication
  • Environments and Postman
  • Sandbox
  • Conventions and naming
  • Legacy names and twins
  • Errors
  • Rate limits and fair use
  • Streaming search results

Concepts

  • Overview
  • Booking flows
  • Passengers and ages
  • Pricing
  • Post-booking operations

Search and price

  • Airport autocomplete
  • Search flights
  • Basic routes
  • Passengers and cabins
  • Filters
  • Supplier selection
  • Open-jaw and multi-city
  • Flexible dates
  • Price an offer

Book, pay and cancel

  • Book
  • Quote a held booking
  • Pay a held booking
  • Cancel a held booking
  • Quote a cancellation
  • Confirm a cancellation

After booking

  • Get a booking
  • Get the ticket PDF
  • Get the ticket number
  • ACD passport uploads
  • Use these docs with AI

Flights · Search and price

Search flights

Search for flights across one, several or every enabled supplier. Start here, then expand the examples by route, passenger, filter, supplier or itinerary type.

POST/api/v1/get_flights

Search available flight offers across every compatible supplier. Results are grouped under suppliers[]: each supplier has its own searchId and its own list of offers.

Permission: Read (a read key is enough; so is a read+write key). Rate group: search, 6,000 requests per minute per key.

Save the supplier-level searchId. Pass suppliers[n].searchId to price_flight and book_flight, never the top-level requestId. A request that fans out to two suppliers returns two searchId values, and an offer can only be priced with the searchId of the supplier entry it is in.

What to expect

  • Size. A search returns 0.7 MB (one-way, two suppliers) to 14 MB of JSON (a busy round trip with 2,000 offers). Send Accept-Encoding: gzip: the same 695 KB response is 26 KB on the wire. There is no pagination: results.totalOffers always equals the length of results.offers.
  • Time. Two to eight seconds, because the response waits for the slowest supplier. To show the first fares after about two seconds, read the results as a stream.
  • Partial results are normal. If at least one supplier answers, the status is 200 and the others are listed in failures[]. Only when no supplier answers is the status 503.
  • Values are read generously, garbage is refused. A value a real client can send ("2" for a count, premium economy for a cabin, a space between airline codes) is read, with a coerced_value warning when its meaning had to be guessed (Conventions). Only a value that makes no sense is a 400 with a stable code, before any supplier is called.
  • Identical searches are merged. Searches with the same parameters that arrive at the same moment from the same agency, environment and currency are merged into one supplier fan-out. Nothing is kept afterwards, and every caller still gets its own requestId and headers and a searchId that works with price_flight.
  • Sandbox suppliers. amadeus_aqc_dz_1 (Amadeus Algeria, only for routes that touch Algeria; supports hold, void and flexible dates) and duffel_1 (Duffel, worldwide; instant ticketing only). See Supplier selection.

Request fields

Route

FieldTypeRequiredDescription
originstringYes¹Departure IATA code: three ASCII letters, an airport (ALG, CDG) or a city (PAR, LON). Lower case is accepted and read as upper case.
destinationstringYes¹Arrival IATA code. Must differ from origin.
departure_datestringYes¹YYYY-MM-DD, a real calendar date from yesterday (time-zone slack) up to 365 days ahead (date_too_far beyond).
return_datestringNoMakes the search a round trip. On or after departure_date, and within the same 365 days.
segmentsarrayNo²1 to 6 flights { origin, destination, departure_date } instead of the four fields above. Dates must not go backwards. See Open-jaw and multi-city.
urlstringNoA path-style search used by FX-Port's own site, for example flights/ALG-CDG/2026-12-15/economy/1adults. It wins over every route field. Prefer the fields above: they are validated field by field.

¹ Required unless segments or url is sent. ² A list of segments replaces origin, destination, departure_date and return_date.

The type of the search comes from the route: one segment is ONE_WAY; two segments where the second is the exact reverse of the first (or return_date) is ROUND_TRIP; two segments that are not reverses is OPEN_JAW; three or more is MULTI_CITY.

Several airports can be written "ALG,ORN" or as a list ["ALG","ORN"] (up to five, in origin and destination only: a segment takes one code): the first one is searched and the others are kept as alternatives that a supplier may ignore (Duffel does). Search one airport per request when you need a predictable result.

Passengers and cabin

FieldTypeRequiredDescription
passengersobjectNoCounts and age lists. Optional: the default is one adult. See Flight passengers & ages.
cabin_classstringNoeconomy (default), premium_economy, business, first or any (no cabin restriction). Case, spaces, dashes and underscores do not matter: Premium Economy, premium-economy and PREMIUM_ECONOMY are the same cabin. premium, economy_class, business_class, first_class and premium_economy_class are read as their cabin with a coerced_value warning, and an empty text means the default cabin. Any other value (coach, Y) is rejected with 400 invalid_cabin_class.

The cabin you send is lower case; the cabin of each segment in the response is upper case (ECONOMY, PREMIUM_ECONOMY, BUSINESS, FIRST).

Filters

FieldTypeDescription
nonstopbooleantrue returns non-stop offers only.
refundablebooleantrue asks the supplier for refundable fares. A hint, not a guarantee: see the table below.
checked_bagsbooleantrue asks for fares with a checked bag included.
max_pricenumberA price ceiling. Not enforced in the sandbox; see below. 0, an empty text and null mean no ceiling: the field is ignored (0 and an empty text add a coerced_value warning). Numeric text ("1500") is read as a number with a warning. A negative or non-numeric value ("cheap", "150000 DZD") is 400 invalid_field_type.
included_airlinesstring[] or textUp to 20 airline codes: ["AF","AH"], or a text with the codes separated by commas, semicolons, bars or spaces ("AF,AH", "AF AH"). Only these carriers.
excluded_airlinesstring[] or textUp to 20 airline codes to remove, written like included_airlines.
preferred_airlinesstring[] or textBehaves exactly like included_airlines: a strict allow-list, not a ranking.
flexiblebooleanAlso returns the date matrix (flexPrices) from suppliers that support it, next to the offers. See Flexible-date search.
flexible_onlybooleanThe matrix without offers. POST /flights/flexible_search sends it for you.
from_cc, to_ccstringISO country codes of the origin and the destination: exactly two letters (DZ; a three-letter value is 400 invalid_country_code). Used to choose suppliers; see Supplier selection.
countriesstring[]Up to 10 country codes of the route, when you want to override the countries FX-Port infers from the airports.
filtersobjectOnly the three airline lists above are read from it. Any other key ({"max_stops": 0}) is ignored.

What each supplier enforces. filtersApplied in the response repeats what you asked for, for every supplier, not what the supplier honoured:

FilterAmadeus Algeria (amadeus_aqc_dz_1)Duffel (duffel_1)
nonstopEnforced.Enforced.
refundableSent to the supplier; the result still mixes refundable and non-refundable fares (70 offers became 53, still mixed).Ignored.
checked_bagsEnforced (included checked bags only).Ignored: offers with no checked bag are returned.
max_priceSent in the supplier's currency (DZD), and not enforced in the sandbox: with max_price: 40000 offers up to 242,844 DZD came back.Never sent; offers up to 280,279 DZD came back.
included_airlines, preferred_airlinesNative carrier restriction: the validating carrier is in the list.A filter on the returned offers: an offer stays when any marketing, operating or validating carrier matches, so validatingAirline can be a carrier you did not list.
excluded_airlinesNative.A filter on the returned offers.

Always read the offer itself (pricing, travelerPricing[].fareDetailsBySegment[].includedCheckedBags, conditions) and filter again on your side when a filter is a hard requirement. You can send included_airlines and excluded_airlines together: the excluded codes are taken out of the included list.

Supplier selection

FieldTypeDescription
(none)Recommended. FX-Port selects the compatible suppliers.
supplier_idstringRestrict the search to one supplier id (a comma separated list is accepted). Strict: an unknown or disabled id is 400 invalid_supplier_selection.
supplier_idsstring[]Restrict the search to this set. Strict, up to 10. Merged with supplier_id.
preferred_suppliersstring[]A hint: ids that are not usable are ignored and the automatic selection applies.
max_suppliersintegerKeep only the first N selected suppliers, in priority order. "3" and 3.0 are read as 3 with a coerced_value warning; an empty text means no limit.

Other fields

FieldTypeDescription
loyalty_program_accountsarrayUp to 10 frequent-flyer accounts { airline_iata_code, account_number, first_name, last_name }. They are stored with the search and matched by passenger name at booking.
acd_exempt_company_idstringFor agencies that settle in DZD and have an ACD-exempt company: its id, to price the fares without ACD. A company that is not linked to your agency is 403 acd_exemption_invalid, a non-DZD agency 403 acd_exemption_currency. See ACD passport uploads.
agent_idstringYour own id of the agent who searches; stored with the search and the booking.

Legacy names

These spellings still work. The response says so in warnings (deprecated_field) and in the headers Deprecation and X-FX-Deprecated-Fields. New code should send the name in the second column. If a request holds a legacy name and its replacement with different values (direct and nonstop), the replacement wins and an ignored_field warning names the dropped one.

Legacy nameUse instead
departureDate, returnDate, cabinClassdeparture_date, return_date, cabin_class
travelerspassengers
directnonstop
checkedBags, maxPrice, flexibleOnlychecked_bags, max_price, flexible_only
fromCc, toCcfrom_cc, to_cc
supplierId, supplierIds, preferredSuppliers, maxSupplierssupplier_id, supplier_ids, preferred_suppliers, max_suppliers
includedAirlines, include_airlines, includeAirlines, included_airline, include_airline, airline_include, airlineIncludeincluded_airlines
excludedAirlines, exclude_airlines, excludeAirlines, excluded_airline, exclude_airline, airline_exclude, airlineExcludeexcluded_airlines
preferredAirlines, airlinespreferred_airlines
passengers.young, passengers.youngAdultspassengers.young_adults
passengers.toddlers, passengers.seatedInfantspassengers.seated_infants
passengers.childAges, youngAdultAges, seatedInfantAges, infantAgespassengers.child_ages, young_adult_ages, seated_infant_ages, infant_ages
segments[].date, segments[].departureDate, segments[].departuresegments[].departure_date
agentId, acdExemptCompanyId, loyaltyProgramAccountsagent_id, acd_exempt_company_id, loyalty_program_accounts

A key the endpoint does not read at all (a typo, the flat adults, max_stops inside filters) never fails the request: it is ignored and reported as an ignored_field warning.

Examples by category

Basic routesOne-way, round trip, non-stop and every-supplier searches.Passengers & cabinsFamily mix, lap and seated infants, senior and young adult, business, premium economy, all cabins.FiltersRefundable, checked bags, price cap, airline include and exclude, flexible dates.Supplier selectionAutomatic selection, exact supplier ids and the routing rules.Open-jaw and multi-cityTwo or more segments.

Minimal request

curl https://api.fx-port.com/api/v1/get_flights \
  -H "Authorization: Bearer fxp_test_YOUR_KEY" \
  -H "Content-Type: application/json" \
  -d '{
  "origin": "ALG",
  "destination": "CDG",
  "departure_date": "2026-12-15",
  "cabin_class": "economy",
  "passengers": {
    "adults": 1
  }
}'

Response essentials

The example is a trimmed real sandbox response to the request above: the Duffel entry with one non-stop offer (the sandbox airline ZZ is Duffel's test carrier). The other supplier's entry has the same shape. Arrays are cut and the amenities list is shortened; the field tables below describe everything that is not shown.

{
  "environment": "sandbox",
  "success": true,
  "requestId": "54139f32",
  "searchType": "ONE_WAY",
  "flexible": false,
  "processingTime": 2.243,
  "suppliers": [
    {
      "success": true,
      "searchId": "fs_dfx_a3aeaa36-74ad-424b-b88d-e6bdc9a4ba94",
      "supportHold": false,
      "supportVoid": false,
      "voidDeadline": null,
      "filtersApplied": {},
      "warnings": [],
      "meta": {
        "supplierId": "duffel_1",
        "technologyType": "duffel",
        "supplierName": "Duffel",
        "processingTime": 1.34,
        "supplierCurrency": "USD",
        "agencyCurrency": "DZD"
      },
      "results": {
        "totalOffers": 92,
        "supplierCurrency": "USD",
        "agencyCurrency": "DZD",
        "offers": [
          {
            "id": "fx_offer_9ab6d940",
            "type": "flight_offer",
            "supplier": { "id": "duffel_1", "name": "Duffel", "originalId": "off_034q6JKdiQDZ8HIDMFus64" },
            "bookableSeats": null,
            "supportHold": false,
            "supportVoid": false,
            "voidDeadline": null,
            "filtersApplied": {},
            "warnings": [],
            "instantTicketingRequired": false,
            "lastTicketingDate": "2026-11-01",
            "lastTicketingDateTime": "2026-11-01T15:52:40.830072Z",
            "pricing": {
              "supplierCurrency": "USD",
              "agencyCurrency": "DZD",
              "basePrice": 16385.0,
              "taxesAndFees": 5226.2,
              "agencyCommission": 21.62,
              "finalPrice": 21632.82,
              "b2bPrice": 21611.2,
              "additionalServices": []
            },
            "itinerary": [
              {
                "direction": "outbound",
                "duration": "PT2H24M",
                "stops": 0,
                "segments": [
                  {
                    "id": "seg_0000BC0a5iUChSV6Qrz0Co",
                    "departure": {
                      "airportCode": "ALG",
                      "airportName": "Houari Boumediene Airport",
                      "cityName": "Algiers",
                      "countryCode": "DZ",
                      "terminal": "2",
                      "datetime": "2026-12-15T10:50:00",
                      "timeZone": "Africa/Algiers"
                    },
                    "arrival": {
                      "airportCode": "CDG",
                      "airportName": "Paris Charles de Gaulle Airport",
                      "cityName": "Paris",
                      "countryCode": "FR",
                      "terminal": "1",
                      "datetime": "2026-12-15T13:14:00",
                      "timeZone": "Europe/Paris"
                    },
                    "flight": {
                      "carrierCode": "ZZ",
                      "carrierName": "Duffel Airways",
                      "carrierLogoUrl": "https://assets.duffel.com/img/airlines/for-light-background/full-color-logo/ZZ.svg",
                      "flightNumber": "7426",
                      "aircraftCode": null,
                      "aircraftName": null,
                      "operatingCarrier": "ZZ",
                      "operatingCarrierName": "Duffel Airways"
                    },
                    "duration": "PT2H24M",
                    "cabin": "ECONOMY",
                    "bookingClass": null,
                    "fareBasis": "Y20LGTN2",
                    "brandedFare": "BASIC",
                    "brandedFareLabel": "Basic"
                  }
                ],
                "conditions": {
                  "changeBeforeDeparture": { "allowed": false },
                  "refundBeforeDeparture": { "allowed": false }
                }
              }
            ],
            "travelerPricing": [
              {
                "travelerId": "pas_0000BC0a5iH5UE0bmBqWkl",
                "travelerType": "ADULT",
                "fareOption": "STANDARD",
                "price": {
                  "supplierCurrency": "USD",
                  "agencyCurrency": "DZD",
                  "base": 16385.0,
                  "total": 21632.82,
                  "b2bPrice": 21611.2
                },
                "fareDetailsBySegment": [
                  {
                    "segmentId": "seg_0000BC0a5iUChSV6Qrz0Co",
                    "cabin": "ECONOMY",
                    "fareBasis": "Y20LGTN2",
                    "brandedFare": "BASIC",
                    "brandedFareLabel": "Basic",
                    "bookingClass": null,
                    "includedCheckedBags": { "quantity": 1 },
                    "includedCabinBags": { "quantity": 1 },
                    "amenities": [
                      { "description": "WIFI", "isChargeable": true, "amenityType": "WIFI", "amenityProvider": { "name": "BrandedFare" } }
                    ]
                  }
                ]
              }
            ],
            "conditions": {
              "refundBeforeDeparture": { "allowed": false },
              "changeBeforeDeparture": { "allowed": false }
            },
            "fareRules": {
              "exchange": { "allowed": false },
              "refund": { "allowed": false },
              "revalidation": { "allowed": false },
              "supplierCurrency": "USD",
              "agencyCurrency": "DZD"
            },
            "validatingAirline": [{ "code": "ZZ", "name": "Duffel Airways" }]
          }
        ]
      },
      "exchangeRate": 250.0
    }
  ],
  "summary": { "totalSuppliers": 2, "successfulSuppliers": 2, "failedSuppliers": 0, "totalOffers": 158 }
}

Names: next to the keys you feed back into the next calls the response adds snake_case twins with the same value. At the top level: request_id, processing_time, search_type. In each supplier entry: search_id, support_hold, support_void, void_deadline, exchange_rate, filters_applied, and meta.supplier_id, meta.supplier_name, meta.processing_time. In each offer: offer_id (next to id), support_hold, support_void, void_deadline, pricing.base_price, pricing.taxes_and_fees, pricing.agency_commission, pricing.final_price, pricing.b2b_price, and passenger_id and passenger_type in each travelerPricing entry. Add ?naming=snake to get every key in snake_case. See Conventions and naming.

Top-level response fields

FieldTypeMeaning
environmentstringsandbox or live, from your key.
successbooleantrue on every 200, even if some suppliers failed: read suppliers[n].success and failures.
requestIdstringThe id of this search, for support.
searchTypestringONE_WAY, ROUND_TRIP, OPEN_JAW or MULTI_CITY, derived from your route.
flexiblebooleanWhether the date matrix was requested.
flexibleOnlybooleanOnly present (and true) for flexible search.
processingTimenumberSeconds spent by the whole search.
suppliersarrayOne entry per supplier that answered; see below.
summaryobjecttotalSuppliers and successfulSuppliers (both count the suppliers that answered), failedSuppliers (the ones listed in failures) and totalOffers.
failuresarrayOnly when a supplier failed: { supplierId, error, cause } (twin: supplier_id). cause is a stable code: supplier_timeout, supplier_api_error, supplier_auth_error, supplier_error, supplier_temporarily_unavailable (the supplier is skipped for a short while), supplier_busy (FX-Port's capacity towards that supplier is full for a moment: the supplier was not called, retry in a few seconds) or service_overloaded (FX-Port was too busy to prepare that supplier's results: retry in a few seconds). error is a fixed sentence about the cause, never the supplier's own text.
warningsarrayOnly when the request used a legacy name, an ignored field or a value that was adjusted. See Conventions and naming.

suppliers[n] fields

FieldTypeMeaning
successbooleanWhether this supplier returned usable results.
searchIdstringSave this. fs_<uuid> (Amadeus Algeria) or fs_dfx_<uuid> (Duffel). Required as search_id by price_flight and book_flight. It is valid for 24 hours, but a supplier withdraws offers earlier: price soon after you show an offer.
supportHold, supportVoidbooleanWhat the supplier can do in general; re-read them on the priced offer before you choose between hold and issue.
voidDeadlinestring or nullISO 8601 UTC: the end of the same-day void window (midnight in the supplier's time zone, Africa/Algiers for Amadeus Algeria). null when the supplier cannot void.
filtersAppliedobjectThe filters you asked for, echoed (see above).
warningsarrayNotes of the supplier; empty in every sample.
metaobjectsupplierId, supplierName, technologyType (amadeus_aqc, duffel), processingTime, supplierCurrency, agencyCurrency.
resultsobjecttotalOffers, supplierCurrency, agencyCurrency, offers.
exchangeRatenumberOnly when the supplier's currency is not your agency's (Duffel, USD to DZD: 250.0).
flexPricesobjectOnly with flexible: true from a supplier that supports it.

offers[n] fields

FieldTypeMeaning
idstringSave this. fx_offer_ and 8 hex characters. Required as offer_id by price and book.
typestringAlways flight_offer.
supplierobjectid, name and originalId (the supplier's own id of the offer: for support only).
bookableSeatsinteger or nullSeats left at this fare, when the supplier says (Amadeus: up to 9).
supportHold, supportVoid, voidDeadlineAs on the supplier, for this offer.
instantTicketingRequiredbooleantrue: the fare cannot be held; book it with booking_type: "issue".
lastTicketingDate, lastTicketingDateTimestringDuffel only: when the offer stops being sellable. Typically 15 to 60 minutes after the search.
pricingobjectEvery field is explained in Flight pricing. Amadeus Algeria adds acd.
itineraryarrayOne entry per direction; see below.
travelerPricingarrayOne entry per priced traveler; see below.
conditionsobjectrefundBeforeDeparture.allowed and changeBeforeDeparture.allowed: indicative, not a promise.
fareRulesobjectexchange, refund, revalidation (each { allowed }) and the two currencies.
validatingAirlinearray{ code, name } of the airline whose rules and ticket stock govern the fare.
additionalServicesarrayAmadeus only: paid extras the supplier lists.
requiresACDbooleanAmadeus Algeria only, present only when true: after booking, passports must be uploaded. See ACD passport uploads.
filtersApplied, warningsAs on the supplier.

itinerary[n] and segments[n] fields

FieldTypeMeaning
directionstringoutbound, return, and segment_3, segment_4 ... for the third and later legs of a multi-city search.
durationstringISO 8601 duration of the direction, for example PT2H24M.
stopsintegerNumber of stops (0 is non-stop).
segments[n].idstringId of the segment; fareDetailsBySegment[].segmentId points to it.
segments[n].departure, .arrivalobjectairportCode, airportName, cityName, countryCode, terminal (can be null), datetime (local time, no zone), timeZone (IANA).
segments[n].flightobjectcarrierCode, carrierName, carrierLogoUrl, flightNumber (without the carrier code: 7426), aircraftCode, aircraftName (can be null), operatingCarrier, operatingCarrierName. Different carriers mean a codeshare.
segments[n].durationstringISO 8601 duration of the flight.
segments[n].cabinstringECONOMY, PREMIUM_ECONOMY, BUSINESS or FIRST for this segment; it can differ from the cabin you asked for.
segments[n].bookingClassstring or nullBooking class letter (Amadeus: Q, O; Duffel: null).
segments[n].fareBasis, .brandedFare, .brandedFareLabelstringFare basis code, fare family code and its display label.
conditionsobjectRefund and change rules of this direction.

travelerPricing[n] fields

FieldTypeMeaning
travelerIdstring"1", "2" ... (Amadeus) or pas_... (Duffel).
travelerTypestringADULT, SENIOR, YOUNG, CHILD, SEATED_INFANT or HELD_INFANT (a lap infant).
fareOptionstringThe fare option, for example STANDARD.
priceobjectThe traveler's share: supplierCurrency, agencyCurrency, base, total, b2bPrice.
fareDetailsBySegment[n]arraysegmentId, cabin, fareBasis, brandedFare, brandedFareLabel, bookingClass, includedCheckedBags.quantity, includedCabinBags.quantity and amenities[] (description, isChargeable, amenityType, amenityProvider).

The entries are grouped by type (adults, then seniors, children ...), not in the order you would list the travelers: a request has no passenger order. Each traveler's price.total adds up to the offer's pricing.finalPrice.

Save these values

ValueWhereUsed by
searchIdsuppliers[n].searchIdprice_flight.search_id, then book_flight.search_id
offer idsuppliers[n].results.offers[m].idprice_flight.offer_id, then book_flight.offer_id
supportHoldsupplier and priced offerChoose hold only when it is still true after pricing
requiresACDofferPlan the ACD passport upload

Streaming

Add ?stream=true (or send Accept: text/event-stream) to receive the same search as server-sent events: a first event after about half a second, the first offers after about two seconds, and the rest as each supplier answers. See Streaming search results for the events, the merge rules, the client code in nine languages and the Cloudflare notes. Keep at most 4 streams open at the same time for one API key.

Errors

The error body is described in Errors. Branch on errors[0].code.

StatusCodeWhenWhat to do
400invalid_json, invalid_bodyThe body is not JSON, or not a JSON object, or is nested more than 24 levels deep, or holds a text longer than 256 characters.Send one JSON object with Content-Type: application/json.
400missing_search_paramsNeither a url, nor segments, nor the three fields origin, destination and departure_date. The body has example_params and example_url.Send a route.
400missing_fieldA segment lacks origin, destination or departure_date. errors[0].field is the path, for example segments[1].departure_date.Send the field it names.
400invalid_airport_codeAn IATA code that is not three ASCII letters (up to five codes in "ALG,ORN"), or an origin equal to the destination.Use three letters; PAR and LON city codes are valid.
400invalid_date, date_in_past, date_too_far, return_before_departureA date that is not a real YYYY-MM-DD, is earlier than yesterday, is more than 365 days ahead, or a return (or a later segment) before the departure.Fix the date.
400invalid_cabin_classcabin_class is not one of the five values, once case, spaces, dashes and underscores are ignored. errors[0].details.allowed lists them.Send one of the five values.
400invalid_passenger_count, invalid_passenger_ageA count that is not a whole number from 0 to 99, or an age that is not a whole number from 0 to 17. Numeric text and integral floats ("2", 2.0) are read with a coerced_value warning; words, fractions, booleans, negatives and bigger numbers are refused.Fix the number.
400traveler_rule_violationThe mix breaks a rule: more than 9 seated passengers, more lap infants than adults and seniors, or more seated infants under 2 than adults and seniors. This answer keeps its older flat body: error: "TRAVELER_RULE_VIOLATION" and violations[] with one entry per broken rule.See Flight passengers & ages.
400invalid_supplier_selectionAn unknown or disabled supplier, or a supplier that cannot do flexible search. availableSuppliers lists the usable ids.Remove the selector or use an available id.
400supplier_passenger_combination_unsupportedNo selected supplier can serve the passenger mix (for example one adult with a seated and a lap infant, with only Duffel available).Change the mix, or select another supplier.
400invalid_airline_filter, invalid_field_type, invalid_segments, invalid_country_code, invalid_currency, invalid_urlA filter or a field has the wrong type or shape; errors[0].field names it.Fix the field.
403acd_exemption_invalid, acd_exemption_currencyacd_exempt_company_id is not usable by this agency.Remove it, or use a company linked to your agency.
413request_too_largeThe body is larger than 64 KB, or holds more than 5,000 values.Send a smaller body.
422no_supplier_supports_flexible_searchflexible_only (or POST /flights/flexible_search) on a route that no flexible-capable supplier serves.Use get_flights for fixed dates.
503all_suppliers_failedNo supplier returned results. supplierErrors[] lists { supplierId, cause, message } with cause one of supplier_timeout, supplier_api_error, supplier_auth_error, supplier_error, supplier_temporarily_unavailable, supplier_busy, service_overloaded and a fixed sentence: the supplier's own text is never returned.A well-formed airport code that does not exist, a date the supplier has no schedule for, or a supplier outage all end here. Wait, then retry with backoff, or search another route.
503supplier_busyEvery supplier refused the search because FX-Port's capacity towards it is full for a moment. The suppliers were not called, nothing was booked and nothing was charged. The answer carries Retry-After (seconds).Wait for Retry-After, then send the same request again: it is safe.
503service_overloadedFX-Port was busy preparing other large search answers and no worker became free within a few seconds, so this search could not be completed. Nothing was booked and nothing was charged. The answer carries Retry-After (seconds).Retry with backoff: wait for Retry-After, then send the same request again.

Invalid input is refused before any supplier is called, so it never costs a supplier request and never counts against a supplier. A supplier that keeps failing is skipped for a short while and listed in failures[] with the cause supplier_temporarily_unavailable; the others still answer. A supplier whose capacity is full for a moment is listed the same way with the cause supplier_busy while the others answer; only when every supplier is busy is the whole search refused with 503 supplier_busy and Retry-After. service_overloaded works like supplier_busy when FX-Port itself was too busy to prepare a supplier's results (one supplier: failures[]; all of them: 503). Neither makes FX-Port skip the supplier for later searches.

Multi-city searches (three or more segments) are not supported by Amadeus Algeria: it fails and is listed in failures, while Duffel answers. Add "supplier_id": "duffel_1" to a multi-city search that touches Algeria to avoid the failing call.

Test it in the sandbox

You wantSend
Both suppliersALG to CDG, one adult, a date 30 days ahead
A fare you can holdA route that touches Algeria; read supportHold on the offer and the supplier amadeus_aqc_dz_1
An instant-only fare"supplier_id": "duffel_1"
An offer that needs ACD passportsCDG to ALG with "supplier_id": "amadeus_aqc_dz_1": every offer has pricing.acd.applied: true
Round trip, open-jaw, multi-cityThe examples of Basic routes and Open-jaw and multi-city
An error"cabin_class": "luxury" returns 400 invalid_cabin_class before any supplier is called
A value that is read, with a warning"passengers": { "adults": "2" } is searched as 2 adults and the answer carries a coerced_value warning; "adults": "two" is 400 invalid_passenger_count

Related

  • Price a flight offer: the required next step.
  • Streaming search results and Flexible-date search.
  • API reference: Search flights and the Flight offer object.
PreviousAirport autocompleteNext Basic route examples

On this page

  • What to expect
  • Request fields
  • Route
  • Passengers and cabin
  • Filters
  • Supplier selection
  • Other fields
  • Legacy names
  • Examples by category
  • Minimal request
  • Response essentials
  • Top-level response fields
  • suppliers[n] fields
  • offers[n] fields
  • itinerary[n] and segments[n] fields
  • travelerPricing[n] fields
  • Save these values
  • Streaming
  • Errors
  • Test it in the sandbox
  • Related

© 2026 FX-Port

TermsPrivacy[email protected]