Routespring Logo
Request Demo

Quickstart

From credentials to crew bookings.

Complete the core sandbox flow: obtain a token, submit a roster snapshot, wait for processing, and inspect the booking decisions RouteSpring derived.

1. Get sandbox credentials

Credentials are issued during onboarding and are scoped to your company. Keep the client secret server-side and never place it in browser code, mobile apps, source control, or support messages.

Access tokens expire in about 15 minutes. Use the returned refresh token atPOST /oauth/refreshor exchange client credentials again.

2. Authenticate

Terminal
export AUTH_BASE="https://oauth-sandbox.routespring.com"

TOKEN_RESPONSE=$(curl -sS -X POST \
  "$AUTH_BASE/oauth/token?grant_type=client_credentials" \
  -u "CLIENT_ID:CLIENT_SECRET")

export ACCESS_TOKEN=$(echo "$TOKEN_RESPONSE" | jq -r .access_token)
export REFRESH_TOKEN=$(echo "$TOKEN_RESPONSE" | jq -r .refresh_token)
export BASE="https://sandbox.routespring.com/api/v1"

3. Submit a schedule

Send a complete snapshot for the date window, not a delta. RouteSpring reconciles it against the previous submission and existing bookings.

Terminal
SCHEDULE=$(curl -sS -X POST "$BASE/crew/schedules" \
  -H "Authorization: Bearer $ACCESS_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "external_ref": "OPS-20260724-001",
    "as_of": "2026-07-24T12:00:00Z",
    "schedule_start_date": "2026-07-24",
    "schedule_end_date": "2026-07-25",
    "pairings": [{
      "pairing_number": "PAIR-001",
      "origin_base": "JFK",
      "crew": [{
        "employee_id": "EMP-1042",
        "name": "Jordan Reyes",
        "rank": "CA",
        "home_base": "JFK",
        "traveller_email": "jreyes@example-air.com"
      }],
      "duty_periods": [{
        "duty_period_num": 1,
        "duty_date": "2026-07-24",
        "fdp_start_local": "2026-07-24T08:00:00-04:00",
        "fdp_end_local": "2026-07-24T18:00:00-05:00",
        "legs": [{
          "leg_sequence": 1,
          "activity_code": "FLT",
          "flight_number": "MX401",
          "from_airport": "JFK",
          "to_airport": "ORD",
          "dep_time_local": "2026-07-24T09:00:00-04:00",
          "arr_time_local": "2026-07-24T10:30:00-05:00"
        }],
        "layover": {
          "station": "ORD",
          "booking_required": true,
          "checkin_time_local": "2026-07-24T11:00:00-05:00",
          "checkout_time_local": "2026-07-25T07:00:00-05:00"
        }
      }]
    }]
  }')

export SCHEDULE_ID=$(echo "$SCHEDULE" | jq -r .schedule_id)
A successful submission returns 202 Accepted, a generated schedule_id, and processing_status: QUEUED.

4. Poll and inspect decisions

Processing is asynchronous. Poll the status endpoint until it reaches a terminal state before treating action items as final.

Terminal
curl -sS "$BASE/crew/schedules/$SCHEDULE_ID/processing-status" \
  -H "Authorization: Bearer $ACCESS_TOKEN" | jq .

# Continue until status is COMPLETED, PARTIAL, or FAILED.
curl -sS "$BASE/crew/schedules/$SCHEDULE_ID/action-items" \
  -H "Authorization: Bearer $ACCESS_TOKEN" | jq .

5. Move beyond the happy path

  • Use GET /crew/bookings to search by booking, schedule, employee, or pairing anchors.
  • Refresh live supplier state with GET /crew/bookings/{booking_id}/status before reading full detail.
  • Use POST /crew/action-items for IROPs and urgent requirements not yet present in the roster.
  • Use retry endpoints only for failed bookings; retries are idempotent and tracked as jobs.