From 555feddabfff5cf1707a925f40926cbda217660b Mon Sep 17 00:00:00 2001 From: vikingowl Date: Mon, 21 Apr 2025 02:49:40 +0200 Subject: [PATCH] Add type-safe API client with utility functions Introduce a type-safe API client using OpenAPI types for ALHP. Implement utility functions `getPackages` and `getStats` for common API usage, and add comprehensive documentation with examples for ease of integration. --- frontend/src/api/README.md | 106 +++++++++++++++++++++++++++++++++++++ frontend/src/api/client.ts | 59 +++++++++++++++++++++ frontend/src/api/index.ts | 6 +++ 3 files changed, 171 insertions(+) create mode 100644 frontend/src/api/README.md create mode 100644 frontend/src/api/client.ts create mode 100644 frontend/src/api/index.ts diff --git a/frontend/src/api/README.md b/frontend/src/api/README.md new file mode 100644 index 0000000..b187a81 --- /dev/null +++ b/frontend/src/api/README.md @@ -0,0 +1,106 @@ +# ALHP API Client + +This directory contains a type-safe API client for the ALHP API, generated from the OpenAPI specification. + +## Usage + +### Importing + +```typescript +// Import the API client and its functions +import { apiClient, getPackages, getStats } from '@/api'; + +// Import types +import type { components } from '@/api'; +``` + +### Fetching Packages + +```typescript +import { getPackages } from '@/api'; +import type { components } from '@/api'; + +// Example: Get packages with filtering +async function fetchPackages() { + try { + const result = await getPackages({ + status: ['latest', 'building'], + pkgbase: 'linux', + exact: false, + repo: 'core-x86-64-v3', + offset: 0, + limit: 50 + }); + + // Access the packages + const packages: components['schemas']['Package'][] = result.packages || []; + const total: number = result.total || 0; + + return { packages, total }; + } catch (error) { + console.error('Failed to fetch packages:', error); + return { packages: [], total: 0 }; + } +} +``` + +### Fetching Stats + +```typescript +import { getStats } from '@/api'; +import type { components } from '@/api'; + +// Example: Get build statistics +async function fetchStats() { + try { + const stats = await getStats(); + + // Access the stats + const failedCount: number = stats.failed || 0; + const ltoEnabled: number = stats.lto?.enabled || 0; + + return stats; + } catch (error) { + console.error('Failed to fetch stats:', error); + return null; + } +} +``` + +### Using the Raw API Client + +If you need more control or want to use endpoints not covered by the utility functions, you can use the raw API client: + +```typescript +import { apiClient } from '@/api'; + +// Example: Custom API call +async function customApiCall() { + const { data, error } = await apiClient.GET('/packages', { + params: { + query: { + // Your custom parameters + status: ['latest'], + limit: 10, + offset: 0 + } + } + }); + + if (error) { + console.error('API error:', error); + return null; + } + + return data; +} +``` + +## Types + +The API client uses types generated from the OpenAPI specification. The main types are: + +- `components['schemas']['Package']`: Type for package data +- `components['schemas']['Stats']`: Type for statistics data + +These types provide full TypeScript intellisense and type checking. diff --git a/frontend/src/api/client.ts b/frontend/src/api/client.ts new file mode 100644 index 0000000..5a94b7d --- /dev/null +++ b/frontend/src/api/client.ts @@ -0,0 +1,59 @@ +import createFetch from 'openapi-fetch' +import type { paths } from '@/generated/alhp' + +// Create a type-safe API client using the OpenAPI types +const apiClient = createFetch({ + baseUrl: import.meta.env.VITE_BASE_URL +}) + +/** + * Get packages with optional filtering + * @param params Query parameters for filtering packages + * @returns Promise with the packages response + */ +export const getPackages = async (params: { + status?: Array< + | 'latest' + | 'failed' + | 'built' + | 'skipped' + | 'delayed' + | 'building' + | 'signing' + | 'unknown' + | 'queued' + > + pkgbase?: string + exact?: boolean + repo?: string + offset: number + limit: number +}) => { + const { data, error } = await apiClient.GET('/packages', { + params: { + query: params + } + }) + + if (error) { + throw new Error(`Failed to fetch packages: ${(error as any).statusCode}`) + } + + return data +} + +/** + * Get build statistics + * @returns Promise with the stats response + */ +export const getStats = async () => { + const { data, error } = await apiClient.GET('/stats') + + if (error) { + throw new Error(`Failed to fetch stats: ${(error as any).statusCode || 'unknown error'}`) + } + + return data +} + +export default apiClient diff --git a/frontend/src/api/index.ts b/frontend/src/api/index.ts new file mode 100644 index 0000000..d5c9efc --- /dev/null +++ b/frontend/src/api/index.ts @@ -0,0 +1,6 @@ +// Export the API client and its functions +export { default as apiClient } from './client'; +export { getPackages, getStats } from './client'; + +// Export types from the generated OpenAPI file +export type { components } from '../generated/alhp';