Skip to main content
GET
/
v1
/
trips
List Trips
curl --request GET \
  --url https://api.bookovia.com/v1/trips \
  --header 'X-API-Key: <api-key>'
{
  "error": {
    "code": "invalid_date_range",
    "message": "Invalid date range specified",
    "details": "start_date must be before end_date"
  }
}

Documentation Index

Fetch the complete documentation index at: https://docs.bookovia.com/llms.txt

Use this file to discover all available pages before exploring further.

Overview

The List Trips endpoint returns a paginated list of trips for your organization with comprehensive filtering and sorting capabilities. Perfect for building dashboards, reports, and fleet management interfaces.
Results are paginated with a default limit of 50 trips per page. Use cursor-based pagination for optimal performance.

Authentication

This endpoint requires authentication via API key in the X-API-Key header. Required permissions: trips:read

Request Parameters

organization_id
string
Filter trips by organization ID (defaults to your authenticated organization)
vehicle_id
string
Filter trips for a specific vehicle
driver_id
string
Filter trips for a specific driver
status
string
Filter by trip status. Options: “active”, “completed”, “cancelled”, “interrupted”
start_date
string
Filter trips starting after this date (ISO 8601 format)
end_date
string
Filter trips starting before this date (ISO 8601 format)
limit
integer
default:"50"
Number of trips to return per page (max 200)
cursor
string
Cursor for pagination (returned in previous response)
sort
string
default:"start_time"
Sort field. Options: “start_time”, “end_time”, “distance”, “duration”, “safety_score”
order
string
default:"desc"
Sort order. Options: “asc”, “desc”
include_analytics
boolean
default:"true"
Whether to include basic analytics for each trip

Request Example

curl -X GET "https://api.bookovia.com/v1/trips?vehicle_id=vehicle_123&status=completed&start_date=2024-04-01T00:00:00Z&limit=25" \
  -H "X-API-Key: bkv_test_your_api_key_here"

Response

trips
array
Array of trip objects matching the filter criteria
pagination
object
Pagination information for navigating results
filters_applied
object
Summary of the filters that were applied to this query

Success Response

{
  "trips": [
    {
      "trip_id": "trip_1234567890abcdef",
      "organization_id": "org_abcdef123456",
      "vehicle_id": "vehicle_123",
      "driver_id": "driver_456",
      "status": "completed",
      "start_time": "2024-04-13T10:30:00Z",
      "end_time": "2024-04-13T12:15:00Z",
      "start_location": {
        "latitude": 40.7128,
        "longitude": -74.0060,
        "address": "New York, NY"
      },
      "end_location": {
        "latitude": 40.7589,
        "longitude": -73.9851,
        "address": "Central Park, NY"
      },
      "metadata": {
        "purpose": "delivery",
        "route_name": "Downtown Route A",
        "priority": "high"
      },
      "analytics": {
        "distance_km": 45.2,
        "duration_minutes": 105,
        "avg_speed_kmh": 32.4,
        "max_speed_kmh": 85,
        "safety_score": 87,
        "eco_score": 82,
        "events_count": 3
      },
      "created_at": "2024-04-13T10:30:00Z",
      "updated_at": "2024-04-13T12:15:00Z"
    },
    {
      "trip_id": "trip_0987654321fedcba",
      "organization_id": "org_abcdef123456",
      "vehicle_id": "vehicle_123",
      "driver_id": "driver_789",
      "status": "completed",
      "start_time": "2024-04-12T14:20:00Z",
      "end_time": "2024-04-12T16:45:00Z",
      "analytics": {
        "distance_km": 32.8,
        "duration_minutes": 145,
        "safety_score": 91,
        "eco_score": 88,
        "events_count": 1
      }
    }
  ],
  "pagination": {
    "total_count": 847,
    "limit": 25,
    "has_more": true,
    "next_cursor": "eyJpZCI6InRyaXBfMDk4NzY1NDMyMWZlZGNiYSIsInRzIjoiMjAyNC0wNC0xMlQxNDoyMDowMFoifQ==",
    "prev_cursor": null
  },
  "filters_applied": {
    "vehicle_id": "vehicle_123",
    "status": "completed",
    "start_date": "2024-04-01T00:00:00Z",
    "sort": "safety_score",
    "order": "desc"
  },
  "summary_stats": {
    "total_distance_km": 12847.6,
    "total_duration_hours": 423.2,
    "avg_safety_score": 84.3,
    "avg_eco_score": 79.8,
    "active_trips": 3,
    "completed_trips": 844
  }
}

Error Responses

{
  "error": {
    "code": "invalid_date_range",
    "message": "Invalid date range specified",
    "details": "start_date must be before end_date"
  }
}

SDK Examples

import Bookovia from '@bookovia/javascript-sdk';

const client = new Bookovia('bkv_test_your_api_key');

// Get recent trips for a vehicle
const recentTrips = await client.trips.list({
  vehicleId: 'vehicle_123',
  limit: 10,
  sort: 'start_time',
  order: 'desc'
});

// Get completed trips for date range
const completedTrips = await client.trips.list({
  status: 'completed',
  startDate: '2024-04-01T00:00:00Z',
  endDate: '2024-04-30T23:59:59Z',
  includeAnalytics: true
});

// Pagination example
let allTrips = [];
let cursor = null;

do {
  const page = await client.trips.list({
    vehicleId: 'vehicle_123',
    limit: 100,
    cursor: cursor
  });
  
  allTrips.push(...page.trips);
  cursor = page.pagination.nextCursor;
} while (cursor);

console.log(`Loaded ${allTrips.length} trips`);

Use Cases

Fleet Dashboard

// Build fleet dashboard with real-time data
const buildFleetDashboard = async () => {
  const [activeTrips, recentCompleted] = await Promise.all([
    // Get currently active trips
    client.trips.list({ status: 'active', includeAnalytics: true }),
    
    // Get recent completed trips for stats
    client.trips.list({
      status: 'completed',
      startDate: new Date(Date.now() - 24*60*60*1000).toISOString(), // Last 24h
      sort: 'end_time',
      order: 'desc'
    })
  ]);
  
  return {
    activeTrips: activeTrips.trips.length,
    avgSafetyScore: recentCompleted.summaryStats.avgSafetyScore,
    totalDistance: recentCompleted.summaryStats.totalDistanceKm,
    activeTripsDetails: activeTrips.trips
  };
};

Driver Performance Report

# Generate driver performance report
async def generate_driver_report(driver_id, days=30):
    end_date = datetime.utcnow()
    start_date = end_date - timedelta(days=days)
    
    trips = await client.trips.list(
        driver_id=driver_id,
        status='completed',
        start_date=start_date.isoformat() + 'Z',
        end_date=end_date.isoformat() + 'Z',
        include_analytics=True,
        limit=200
    )
    
    if not trips.trips:
        return {"error": "No trips found for driver"}
    
    # Calculate averages
    total_trips = len(trips.trips)
    avg_safety = sum(t.analytics.safety_score for t in trips.trips) / total_trips
    avg_eco = sum(t.analytics.eco_score for t in trips.trips) / total_trips
    total_distance = sum(t.analytics.distance_km for t in trips.trips)
    
    return {
        "driver_id": driver_id,
        "period_days": days,
        "total_trips": total_trips,
        "total_distance_km": total_distance,
        "avg_safety_score": avg_safety,
        "avg_eco_score": avg_eco,
        "trips_per_day": total_trips / days
    }

Route Analysis

// Analyze route efficiency across multiple trips
func analyzeRouteEfficiency(vehicleID string, routeName string) (*RouteAnalysis, error) {
    trips, err := client.Trips.List(context.Background(), &bookovia.ListTripsOptions{
        VehicleID: vehicleID,
        Status: "completed",
        IncludeAnalytics: true,
        Limit: 200,
    })
    
    if err != nil {
        return nil, err
    }
    
    // Filter trips by route name in metadata
    var routeTrips []*bookovia.Trip
    for _, trip := range trips.Trips {
        if trip.Metadata["route_name"] == routeName {
            routeTrips = append(routeTrips, trip)
        }
    }
    
    if len(routeTrips) == 0 {
        return nil, fmt.Errorf("no trips found for route: %s", routeName)
    }
    
    // Calculate route statistics
    var totalDistance, totalDuration float64
    var totalSafetyScore int
    
    for _, trip := range routeTrips {
        totalDistance += trip.Analytics.DistanceKm
        totalDuration += trip.Analytics.DurationMinutes
        totalSafetyScore += trip.Analytics.SafetyScore
    }
    
    return &RouteAnalysis{
        RouteName: routeName,
        TripCount: len(routeTrips),
        AvgDistance: totalDistance / float64(len(routeTrips)),
        AvgDuration: totalDuration / float64(len(routeTrips)),
        AvgSafetyScore: totalSafetyScore / len(routeTrips),
    }, nil
}

Best Practices

Efficient Pagination

  • Always use cursor-based pagination for consistent results
  • Store cursors for navigation between pages
  • Use appropriate page sizes (25-100 items)
  • Apply specific filters to reduce result sets
  • Use date ranges to limit time scope
  • Filter by vehicle_id or driver_id when possible

Data Loading Strategies

// Load critical data first, then details
const criticalData = await client.trips.list({ 
  status: 'active', 
  includeAnalytics: false 
});

// Load detailed analytics separately
const detailedData = await Promise.all(
  criticalData.trips.map(trip => 
    client.trips.get(trip.tripId, { analyticsLevel: 'standard' })
  )
);

Next Steps

Get Trip Details

Get detailed information for specific trips

Trip Analytics

Get comprehensive analytics for completed trips

Fleet Overview

Organization-wide fleet analytics and metrics

Safety Analytics

Deep dive into safety performance analysis