Adrasis™

Transfers

Search, prebook, and book airport and point-to-point transfers: shared per-passenger and private per-vehicle offers over a zone-to-zone route.

Transfers are a single-product vertical (product_type 2) with the same three-step booking flow as accommodation: search, prebook, and book. The flow uses a route rather than a stay. A route is a zone pair (from_zone → to_zone) for a direction and a service date.

  • SHARED offers price per passenger: an adult base plus age-resolved children.
  • PRIVATE offers price per vehicle, independent of the passenger count.

All three endpoints require the distribution:booking scope.

POST /api/v1/transfer/search

Returns priced offers for the route, direction, and party. direction is 1 for arrival or 2 for departure. service_class filters the result: 0 for both, 1 for private only, 2 for shared only. vehicle_type_public_id is optional and narrows private offers to one vehicle type. currency_code is required and must be a three-letter uppercase ISO 4217 code. language is a BCP 47 tag such as tr-TR; the server canonicalizes its casing, a malformed tag answers 400, and a well-formed tag the catalogue does not carry falls back to the default language.

Both zones, direction, service_date, the party, service_class, vehicle_type_public_id, currency_code and language are all bound into the allocation_id. Prebook replays this request, so every one of them must be repeated there exactly as you sent it here.

curl -s -X POST \
  https://ari.console.adrasis.com/api/v1/transfer/search \
  -H 'Authorization: Bearer eyJ...' \
  -H 'Content-Type: application/json' \
  -d '{
    "from_zone_public_id": "zn_Airport01",
    "to_zone_public_id": "zn_Hotel77",
    "direction": 1,
    "service_date": "2026-07-04",
    "adults": 2,
    "child_ages": [6],
    "service_class": 0,
    "currency_code": "EUR",
    "language": "en"
  }'
{
  "offers": [
    {
      "allocation_id": "alc_7a9e4c82b31d605ff09428ac37e612bd",
      "from_zone_public_id": "zn_Airport01",
      "to_zone_public_id": "zn_Hotel77",
      "direction": 1,
      "service_class": 2,
      "service_date": "2026-07-04",
      "total_selling_rate": "54.00",
      "currency_id": 978,
      "currency_code": "EUR"
    }
  ],
  "dropped": [],
  "trace_id": "0f2c9d6e-7b1a-4c3e-9a2f-1d6e7b1a4c3e"
}

total_selling_rate is the party total, and currency_code states the currency it is denominated in. Transfer search does not convert: it returns only rates already held in the currency you asked for, so currency_code always equals the requested currency_code. A route priced solely in another currency returns no offers rather than a converted amount; ask for that currency instead.

Rates the party could not be priced on (for example a child age outside a shared tariff) are returned under dropped rather than failing the request.

Branch on dropped[].reason_code, not on the sentence in reason. When the response carries no offers and a single no_rate entry, nothing the request named has a live rate for that date: a zone id may be wrong, the route may sit outside your catalogue, or it may have no supply. Those three deliberately share one code. Carry the chosen allocation_id and the exact route-search fields into prebook.

Step 2: Prebook

POST /api/v1/transfer/prebook

Replays the exact route search, resolves and re-prices the chosen allocation, then mints a short-lived prebook token. A changed search boundary cannot select a different offer; a withdrawn or sold-out allocation returns 410 Gone.

Send back the search request, not the offer. The example below searched with service_class: 0 and no vehicle filter, so it prebooks the same way even though the chosen offer reports service_class: 2. Copying the offer's values into the prebook body describes a narrower search than the one that priced the offer, which mints a different allocation_id, matches nothing, and returns 410 Gone.

curl -s -X POST \
  https://ari.console.adrasis.com/api/v1/transfer/prebook \
  -H 'Authorization: Bearer eyJ...' \
  -H 'Content-Type: application/json' \
  -d '{
    "allocation_id": "alc_7a9e4c82b31d605ff09428ac37e612bd",
    "from_zone_public_id": "zn_Airport01",
    "to_zone_public_id": "zn_Hotel77",
    "direction": 1,
    "service_date": "2026-07-04",
    "adults": 2,
    "child_ages": [6],
    "service_class": 0,
    "currency_code": "EUR",
    "language": "en"
  }'
{
  "match_status": "MATCHED",
  "prebook_token": "<PREBOOK_TOKEN>",
  "prebook_expires_at": "2026-07-01T12:30:00Z",
  "offer": {
    "allocation_id": "alc_7a9e4c82b31d605ff09428ac37e612bd",
    "from_zone_public_id": "zn_Airport01",
    "to_zone_public_id": "zn_Hotel77",
    "direction": 1,
    "service_class": 2,
    "service_date": "2026-07-04",
    "total_selling_rate": "54.00",
    "currency_id": 978,
    "currency_code": "EUR"
  },
  "trace_id": "0f2c9d6e-7b1a-4c3e-9a2f-1d6e7b1a4c3e"
}

Inspect match_status before booking. MATCHED is safe to finalize; a moved price or unavailable offer is reported there exactly as for accommodation (see The booking flow).

Step 3: Book

Book requires your partner account to settle on account with the seller. Without those terms it returns 422 PAYMENT_INTENT_NOT_SUPPORTED before writing the booking. An optional payment_intent_kind may confirm the resolved INVOICE intent; it cannot select different terms. Omit it to use your account's terms. Search results and a prebook token do not replace this book-time check. See Booking payment terms.

POST /api/v1/transfer/book

Verifies the prebook token and writes a single-product transfer booking. The Idempotency-Key header is mandatory. A replay returns 200; a conflicting reuse returns 409 (see Idempotency).

curl -s -X POST \
  https://ari.console.adrasis.com/api/v1/transfer/book \
  -H 'Authorization: Bearer eyJ...' \
  -H 'Idempotency-Key: 3b2a1c0d-5e6f-4a8b-9c0d-1e2f3a4b5c6d' \
  -H 'Content-Type: application/json' \
  -d '{
    "prebook_token": "<PREBOOK_TOKEN>",
    "contact": {
      "first_name": "Ada",
      "last_name": "Lovelace",
      "email": "ada@example.io",
      "phone": "+441234567890"
    },
    "agency_reference": "your-ref-12345"
  }'
{
  "booking": {
    "public_id": "bk_Tf81nQ4p",
    "booking_number": 100731,
    "status": "CONFIRMED",
    "product_type": 2,
    "total_amount": "54.00",
    "currency_code": "EUR"
  },
  "trace_id": "0f2c9d6e-7b1a-4c3e-9a2f-1d6e7b1a4c3e"
}

Cancellation

A transfer booking uses the canonical two-phase cancellation flow: cancellation-quote, then cancel, on /bookings/{public_id}. Accommodation uses the same flow. See The booking flow. To group a transfer with other bookings into one itinerary, see Trip bundling.