Skip to main content

Python SDK

The Bundleport Python SDK provides a simple, type-safe client for the Connect Hotels REST API.

Install

pip install bundleport-connect-hotels

Initialize the Client

from bundleport import BundleportClient

client = BundleportClient(
api_key='YOUR_API_KEY_HERE',
base_url='https://api.bundleport.com', # Optional, defaults to production
timeout=30, # Optional, request timeout in seconds
)

Booking Operations

Search for Hotels (Availability)

search_result = client.hotels.search_availability(
criteria={
'checkIn': '2025-06-15T00:00:00Z',
'checkOut': '2025-06-17T00:00:00Z',
'occupancies': [
{
'paxes': [
{'name': 'John', 'surname': 'Doe', 'age': 35},
{'name': 'Jane', 'surname': 'Doe', 'age': 33},
{'name': 'Child', 'surname': 'Doe', 'age': 8},
],
}
],
'hotels': ['12345', '67890'], # Optional: specific hotel codes
'currency': 'EUR',
'language': 'en',
'nationality': 'US',
},
settings={
'connectionCodes': ['testb-hbds-1876'],
'timeout': 30000,
},
)

print(f"Found {len(search_result['options'])} options")

Get Prebooking Quote

quote_result = client.hotels.get_prebooking(
criteria={
'optionRefId': search_result['options'][0]['optionRefId'],
},
settings={'connectionCodes': ['testb-hbds-1876']},
)

# Check for price changes
warnings = quote_result.get('warnings', [])
if any(w.get('code') == 'PRICE_CHANGED' for w in warnings):
print('Price has changed:', quote_result['optionQuote']['price'])

Create a Booking

booking = client.hotels.create_booking(
input={
'optionRefId': quote_result['optionQuote']['optionRefId'],
'holder': {
'name': 'John',
'surname': 'Doe',
'title': 'MR',
},
'rooms': [
{
'occupancyRefId': 1,
'paxes': [
{'name': 'John', 'surname': 'Doe', 'age': 35},
{'name': 'Jane', 'surname': 'Doe', 'age': 33},
],
}
],
'paymentCard': {
'type': 'VI',
'number': '4111111111111111',
'expire': {'month': 12, 'year': 2027},
'holder': {
'name': 'John',
'surname': 'Doe',
'contactInfo': {
'email': 'john.doe@example.com',
'phone': {'countryCode': '+34', 'number': '600123456'},
},
},
},
'clientReference': 'BOOKING-2025-001',
},
settings={
'connectionCodes': ['testb-hbds-1876'],
},
)

print(f"Booking confirmed: {booking['booking']['bookingID']}")

Retrieve Booking Details

booking_details = client.hotels.get_booking_detail(
criteria={
'bookingID': 'BK-987654321',
},
settings={
'connectionCodes': ['testb-hbds-1876'],
},
)
print(f"Booking status: {booking_details['booking']['status']}")

List Bookings

bookings = client.hotels.list_bookings(
criteria={
'typeSearch': 'BOOKING_LIST_CRITERIA_TYPE_DATES',
'dates': {
'dateType': 'BOOKING_LIST_CRITERIA_DATE_TYPE_ARRIVAL',
'start': '2025-06-01T00:00:00Z',
'end': '2025-06-30T00:00:00Z',
},
# Or search by booking ID:
# 'typeSearch': 'BOOKING_LIST_CRITERIA_TYPE_BOOKING_ID',
# 'bookingID': 'BK-987654321',
},
settings={
'connectionCodes': ['testb-hbds-1876'],
},
)

print(f"Found {len(bookings['bookings'])} bookings")

Cancel Booking

cancel_result = client.hotels.cancel(
input={
'bookingID': 'BK-987654321',
},
settings={
'connectionCodes': ['testb-hbds-1876'],
},
)

print(f"Cancellation status: {cancel_result['cancel']['status']}")
if cancel_result['cancel'].get('cancelPenalties'):
for penalty in cancel_result['cancel']['cancelPenalties']:
print(f"Cancellation penalty: {penalty['value']} {penalty['currency']}")

Content Operations

Get Hotels

hotels = client.content.get_hotels(
query={
'destinationCodes': ['BCN'],
'maxSize': 100,
},
)

print(f"Found {len(hotels['hotels']['hotels'])} hotels")

Get Rooms

rooms = client.content.get_rooms(
query={
'connectionCode': 'CONN_1',
'maxSize': 50,
},
)

Get Destinations

destinations = client.content.get_destinations(
query={'maxSize': 100},
)

Error Handling

from bundleport.exceptions import BundleportError, UnauthorizedError, RateLimitError

try:
result = client.hotels.search_availability({...})
except UnauthorizedError:
print('Invalid API key')
except RateLimitError as e:
print(f'Rate limit exceeded, retry after: {e.retry_after} seconds')
except BundleportError as e:
print(f'API error: {e.message}')

Next Steps