@drfrost/bods-js
Version:
JavaScript client for the UK's Bus Open Data Service (BODS) API
152 lines (144 loc) • 4.37 kB
text/typescript
import type { Timetable, TimetableResponse, TimetableSearchParams } from '../types/timetables.js';
import { HttpClient } from './http-client.js';
/**
* Client for interacting with the BODS Timetables API
*
* The Timetables API provides access to bus schedule and route information.
* Data is updated every 24 hours around 06:00 GMT.
*/
export class TimetablesClient {
constructor(private httpClient: HttpClient) {}
/**
* Search for timetable datasets
*
* @param params - Search parameters to filter timetables
* @returns Promise resolving to paginated timetable results
*
* @example
* ```typescript
* // Find all timetables for a specific operator
* const timetables = await client.timetables.search({
* noc: ['SCMN'],
* status: 'published'
* });
*
* // Search by administrative area
* const areaTimetables = await client.timetables.search({
* adminArea: ['060'], // Cheshire East
* limit: 50
* });
*
* // Search with text query
* const searchResults = await client.timetables.search({
* search: 'Stagecoach',
* dqRag: 'green'
* });
* ```
*/
async search(params: TimetableSearchParams = {}): Promise<TimetableResponse> {
const response = await this.httpClient.get<TimetableResponse>('/api/v1/dataset', params);
return response.data;
}
/**
* Get a specific timetable dataset by ID
*
* @param datasetId - The unique dataset identifier
* @returns Promise resolving to the timetable dataset
*
* @example
* ```typescript
* const timetable = await client.timetables.getById(86);
* console.log(timetable.operatorName, timetable.lines);
* ```
*/
async getById(datasetId: number): Promise<Timetable> {
const response = await this.httpClient.get<Timetable>(`/api/v1/dataset/${datasetId}`);
return response.data;
}
/**
* Get all timetables for a specific operator
*
* @param noc - National Operator Code(s)
* @param additionalParams - Additional search parameters
* @returns Promise resolving to paginated timetable results
*
* @example
* ```typescript
* const operatorTimetables = await client.timetables.getByOperator(['SCMN', 'SCGH']);
* ```
*/
async getByOperator(
noc: string | string[],
additionalParams: Omit<TimetableSearchParams, 'noc'> = {}
): Promise<TimetableResponse> {
return this.search({
...additionalParams,
noc: Array.isArray(noc) ? noc : [noc]
});
}
/**
* Get timetables for a specific administrative area
*
* @param adminArea - Administrative area code(s)
* @param additionalParams - Additional search parameters
* @returns Promise resolving to paginated timetable results
*
* @example
* ```typescript
* const areaTimetables = await client.timetables.getByAdminArea('060');
* ```
*/
async getByAdminArea(
adminArea: string | string[],
additionalParams: Omit<TimetableSearchParams, 'adminArea'> = {}
): Promise<TimetableResponse> {
return this.search({
...additionalParams,
adminArea: Array.isArray(adminArea) ? adminArea : [adminArea]
});
}
/**
* Get recently modified timetables
*
* @param since - Date to check for modifications since
* @param additionalParams - Additional search parameters
* @returns Promise resolving to paginated timetable results
*
* @example
* ```typescript
* const recent = await client.timetables.getRecentlyModified(
* new Date('2023-01-01')
* );
* ```
*/
async getRecentlyModified(
since: Date | string,
additionalParams: Omit<TimetableSearchParams, 'modifiedDate'> = {}
): Promise<TimetableResponse> {
return this.search({
...additionalParams,
modifiedDate: since
});
}
/**
* Get high-quality timetables (green data quality rating)
*
* @param additionalParams - Additional search parameters
* @returns Promise resolving to paginated timetable results
*
* @example
* ```typescript
* const qualityTimetables = await client.timetables.getHighQuality({
* bodsCompliance: true
* });
* ```
*/
async getHighQuality(
additionalParams: Omit<TimetableSearchParams, 'dqRag'> = {}
): Promise<TimetableResponse> {
return this.search({
...additionalParams,
dqRag: 'green'
});
}
}