UNPKG

autotrader-connect-api

Version:

Production-ready TypeScript wrapper for Auto Trader UK Connect APIs

283 lines 11.3 kB
/** * AutoTrader Connect API - Main Entry Point * Production-ready TypeScript wrapper for Auto Trader UK Connect APIs * * @author Your Organization * @version 1.0.0 * @license MIT */ // Core exports export { ApiClient, getClient } from './client'; export { AuthManager, getAuthManager, getToken } from './auth'; // Import for internal use import { getClient } from './client'; import { getToken } from './auth'; import { getAdvertiser } from './modules/advertisers'; // Vehicle-related exports export * from './modules/vehicles'; export { searchVehicles as searchVehiclesAdvanced, quickSearch, getSearchSuggestions, saveSearch, getSavedSearches, updateSavedSearch, deleteSavedSearch, executeSavedSearch, compareVehicles, getPopularSearches, getSearchAnalytics, trackSearchInteraction, getRelatedSearches, getMarketInsights } from './modules/search'; export * from './modules/stock'; export * from './modules/images'; export * from './modules/valuations'; export * from './modules/taxonomy'; // Placeholder exports for other modules // These would be fully implemented in a production environment export * from './modules/vehicleMetrics'; export * from './modules/futureValuations'; export * from './modules/historicValuations'; // Export specific functions to avoid conflicts export { getResource as getDeals, listResources as listDeals } from './modules/deals'; export { getResource as getMessages, listResources as listMessages } from './modules/messages'; export { getResource as getPartExchange, listResources as listPartExchange } from './modules/partExchange'; export { getResource as getDelivery, listResources as listDelivery } from './modules/delivery'; export { getResource as getCalls, listResources as listCalls } from './modules/calls'; export { getResource as getCoDriver, listResources as listCoDriver } from './modules/coDriver'; export { getResource as getFinance, listResources as listFinance } from './modules/finance'; // Advertiser management exports export { getCurrentAdvertiser, getAdvertiser, searchAdvertisers, getAllAdvertisers, updateAdvertiser, getAdvertiserStats, getAdvertiserVehicleCount, getNearbyAdvertisers, getTopRatedAdvertisers, getResource as getAdvertisers, listResources as listAdvertisers } from './modules/advertisers'; // Type exports export * from './types/common'; export * from './types/auth'; export * from './types/vehicle'; export * from './types/stock'; export * from './types/search'; // Default client instance import client from './client'; export default client; /** * Package version */ export const VERSION = '1.0.0'; /** * Package name */ export const PACKAGE_NAME = 'autotrader-connect-api'; /** * Initialize the AutoTrader Connect API client with configuration * @param config API client configuration * @returns Configured API client instance */ export function initializeClient(config) { const clientConfig = { apiKey: config.apiKey, apiSecret: config.apiSecret, baseURL: config.baseURL || 'https://api.autotrader.co.uk', ...(config.timeout && { timeout: config.timeout }), ...(config.maxRetries && { maxRetries: config.maxRetries }), ...(config.rateLimitRequests && { rateLimitRequests: config.rateLimitRequests }), ...(config.rateLimitWindow && { rateLimitWindow: config.rateLimitWindow }), ...(config.debug !== undefined && { debug: config.debug }), }; return getClient(clientConfig); } /** * Quick setup with environment variables for rapid development * Automatically detects sandbox vs production based on NODE_ENV * @param options Optional configuration overrides * @returns Configured API client instance */ export function quickSetup(options) { // Determine environment let useSandbox = process.env['NODE_ENV'] === 'development' || process.env['NODE_ENV'] === 'test'; if (options?.forceSandbox) { useSandbox = true; } else if (options?.forceProduction) { useSandbox = false; } else if (process.env['AT_USE_SANDBOX']) { useSandbox = process.env['AT_USE_SANDBOX'] === 'true'; } // Get appropriate credentials const apiKey = useSandbox ? process.env['AT_SANDBOX_API_KEY'] : process.env['AT_API_KEY']; const apiSecret = useSandbox ? process.env['AT_SANDBOX_API_SECRET'] : process.env['AT_API_SECRET']; const baseURL = useSandbox ? (process.env['AT_SANDBOX_BASE_URL'] || 'https://sandbox-api.autotrader.co.uk') : (process.env['AT_BASE_URL'] || 'https://api.autotrader.co.uk'); if (!apiKey || !apiSecret) { const envPrefix = useSandbox ? 'AT_SANDBOX_' : 'AT_'; throw new Error(`Missing API credentials for ${useSandbox ? 'sandbox' : 'production'} environment. ` + `Please set ${envPrefix}API_KEY and ${envPrefix}API_SECRET environment variables.`); } const clientConfig = { apiKey, apiSecret, baseURL, useSandbox, ...(options?.timeout && { timeout: options.timeout }), ...(options?.debug !== undefined && { debug: options.debug }), }; return getClient(clientConfig); } /** * Setup client specifically for sandbox/testing environment * @param credentials Sandbox API credentials * @param options Optional configuration overrides * @returns Configured API client for sandbox */ export function setupSandbox(credentials, options) { let apiKey; let apiSecret; let baseURL; if (credentials) { apiKey = credentials.apiKey; apiSecret = credentials.apiSecret; baseURL = credentials.baseURL || 'https://sandbox-api.autotrader.co.uk'; } else { // Use environment variables apiKey = process.env['AT_SANDBOX_API_KEY'] || ''; apiSecret = process.env['AT_SANDBOX_API_SECRET'] || ''; baseURL = process.env['AT_SANDBOX_BASE_URL'] || 'https://sandbox-api.autotrader.co.uk'; if (!apiKey || !apiSecret) { throw new Error('Sandbox credentials required. Provide credentials or set AT_SANDBOX_API_KEY and AT_SANDBOX_API_SECRET environment variables.'); } } const clientConfig = { apiKey, apiSecret, baseURL, useSandbox: true, debug: options?.debug ?? true, // Default to debug mode in sandbox ...(options?.timeout && { timeout: options.timeout }), }; return getClient(clientConfig); } /** * Setup client specifically for production environment * @param credentials Production API credentials * @param options Optional configuration overrides * @returns Configured API client for production */ export function setupProduction(credentials, options) { let apiKey; let apiSecret; let baseURL; if (credentials) { apiKey = credentials.apiKey; apiSecret = credentials.apiSecret; baseURL = credentials.baseURL || 'https://api.autotrader.co.uk'; } else { // Use environment variables apiKey = process.env['AT_API_KEY'] || ''; apiSecret = process.env['AT_API_SECRET'] || ''; baseURL = process.env['AT_BASE_URL'] || 'https://api.autotrader.co.uk'; if (!apiKey || !apiSecret) { throw new Error('Production credentials required. Provide credentials or set AT_API_KEY and AT_API_SECRET environment variables.'); } } const clientConfig = { apiKey, apiSecret, baseURL, useSandbox: false, debug: options?.debug ?? false, // Default to no debug in production ...(options?.timeout && { timeout: options.timeout }), }; return getClient(clientConfig); } /** * Create a client scoped to a specific advertiser * @param advertiserId Advertiser ID to scope all operations to * @param options Optional configuration overrides * @returns Configured API client with advertiser context */ export function createAdvertiserClient(advertiserId, options) { const baseClient = quickSetup(options); // Create a wrapper object that injects advertiserId into all requests const advertiserClient = { // Include all other client methods and properties first ...baseClient, // Override HTTP methods to inject advertiserId get: async (url, requestOptions) => { const params = { ...requestOptions?.params, advertiserId }; return baseClient.get(url, { ...requestOptions, params }); }, post: async (url, data, requestOptions) => { const enrichedData = data ? { ...data, advertiserId } : { advertiserId }; return baseClient.post(url, enrichedData, requestOptions); }, put: async (url, data, requestOptions) => { const enrichedData = data ? { ...data, advertiserId } : { advertiserId }; return baseClient.put(url, enrichedData, requestOptions); }, patch: async (url, data, requestOptions) => { const enrichedData = data ? { ...data, advertiserId } : { advertiserId }; return baseClient.patch(url, enrichedData, requestOptions); }, delete: async (url, requestOptions) => { const params = { ...requestOptions?.params, advertiserId }; return baseClient.delete(url, { ...requestOptions, params }); }, // Add advertiser context advertiserId, }; return advertiserClient; } /** * Validate advertiser ID format and existence * @param advertiserId Advertiser ID to validate * @returns Promise resolving to validation result */ export async function validateAdvertiserId(advertiserId) { try { if (!Number.isInteger(advertiserId) || advertiserId <= 0) { return { valid: false, error: 'Advertiser ID must be a positive integer' }; } const advertiser = await getAdvertiser(advertiserId); return { valid: true, exists: true, advertiserName: advertiser.name }; } catch (error) { if (error.response?.status === 404) { return { valid: true, exists: false, error: 'Advertiser not found' }; } return { valid: false, error: error.message || 'Unknown error validating advertiser ID' }; } } /** * Health check function to verify API connectivity */ export async function healthCheck() { const startTime = Date.now(); try { const client = getClient(); // Attempt to get a token to verify auth await getToken(); // Simple API call to verify connectivity // This would typically be a lightweight endpoint like /health or /status await client.get('/health'); const latency = Date.now() - startTime; return { status: 'healthy', timestamp: new Date().toISOString(), version: VERSION, auth: true, latency, }; } catch (error) { return { status: 'unhealthy', timestamp: new Date().toISOString(), version: VERSION, auth: false, error: error instanceof Error ? error.message : 'Unknown error', }; } } //# sourceMappingURL=index.js.map