Backup: 2025-06-07 19:48 - Script test
[Restore from backup: vip-coordinator-backup-2025-06-07-19-48-script-test]
This commit is contained in:
109
frontend/src/api/client.ts
Normal file
109
frontend/src/api/client.ts
Normal file
@@ -0,0 +1,109 @@
|
||||
// Simplified API client that handles all the complexity in one place
|
||||
// Use empty string for relative URLs when no API URL is specified
|
||||
const API_BASE_URL = import.meta.env.VITE_API_URL || '';
|
||||
|
||||
class ApiClient {
|
||||
private baseURL: string;
|
||||
|
||||
constructor(baseURL: string) {
|
||||
this.baseURL = baseURL;
|
||||
}
|
||||
|
||||
private getAuthHeaders(): HeadersInit {
|
||||
const token = localStorage.getItem('authToken');
|
||||
return {
|
||||
'Content-Type': 'application/json',
|
||||
...(token && { Authorization: `Bearer ${token}` })
|
||||
};
|
||||
}
|
||||
|
||||
private async handleResponse<T>(response: Response): Promise<T> {
|
||||
if (!response.ok) {
|
||||
const error = await response.json().catch(() => ({ error: response.statusText }));
|
||||
throw new Error(error.error?.message || error.error || `Request failed: ${response.status}`);
|
||||
}
|
||||
return response.json();
|
||||
}
|
||||
|
||||
// Generic request method
|
||||
private async request<T>(endpoint: string, options: RequestInit = {}): Promise<T> {
|
||||
const url = `${this.baseURL}${endpoint}`;
|
||||
const response = await fetch(url, {
|
||||
...options,
|
||||
headers: {
|
||||
...this.getAuthHeaders(),
|
||||
...options.headers
|
||||
}
|
||||
});
|
||||
return this.handleResponse<T>(response);
|
||||
}
|
||||
|
||||
// Convenience methods
|
||||
async get<T>(endpoint: string): Promise<T> {
|
||||
return this.request<T>(endpoint);
|
||||
}
|
||||
|
||||
async post<T>(endpoint: string, data?: any): Promise<T> {
|
||||
return this.request<T>(endpoint, {
|
||||
method: 'POST',
|
||||
body: data ? JSON.stringify(data) : undefined
|
||||
});
|
||||
}
|
||||
|
||||
async put<T>(endpoint: string, data?: any): Promise<T> {
|
||||
return this.request<T>(endpoint, {
|
||||
method: 'PUT',
|
||||
body: data ? JSON.stringify(data) : undefined
|
||||
});
|
||||
}
|
||||
|
||||
async delete<T>(endpoint: string): Promise<T> {
|
||||
return this.request<T>(endpoint, { method: 'DELETE' });
|
||||
}
|
||||
|
||||
async patch<T>(endpoint: string, data?: any): Promise<T> {
|
||||
return this.request<T>(endpoint, {
|
||||
method: 'PATCH',
|
||||
body: data ? JSON.stringify(data) : undefined
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
// Export a singleton instance
|
||||
export const api = new ApiClient(API_BASE_URL);
|
||||
|
||||
// Export specific API methods for better type safety and convenience
|
||||
export const vipApi = {
|
||||
list: () => api.get<any[]>('/api/vips'),
|
||||
get: (id: string) => api.get<any>(`/api/vips/${id}`),
|
||||
create: (data: any) => api.post<any>('/api/vips', data),
|
||||
update: (id: string, data: any) => api.put<any>(`/api/vips/${id}`, data),
|
||||
delete: (id: string) => api.delete<any>(`/api/vips/${id}`),
|
||||
getSchedule: (id: string) => api.get<any[]>(`/api/vips/${id}/schedule`)
|
||||
};
|
||||
|
||||
export const driverApi = {
|
||||
list: () => api.get<any[]>('/api/drivers'),
|
||||
get: (id: string) => api.get<any>(`/api/drivers/${id}`),
|
||||
create: (data: any) => api.post<any>('/api/drivers', data),
|
||||
update: (id: string, data: any) => api.put<any>(`/api/drivers/${id}`, data),
|
||||
delete: (id: string) => api.delete<any>(`/api/drivers/${id}`),
|
||||
getSchedule: (id: string) => api.get<any[]>(`/api/drivers/${id}/schedule`)
|
||||
};
|
||||
|
||||
export const scheduleApi = {
|
||||
create: (vipId: string, data: any) => api.post<any>(`/api/vips/${vipId}/schedule`, data),
|
||||
update: (vipId: string, eventId: string, data: any) =>
|
||||
api.put<any>(`/api/vips/${vipId}/schedule/${eventId}`, data),
|
||||
delete: (vipId: string, eventId: string) =>
|
||||
api.delete<any>(`/api/vips/${vipId}/schedule/${eventId}`),
|
||||
updateStatus: (vipId: string, eventId: string, status: string) =>
|
||||
api.patch<any>(`/api/vips/${vipId}/schedule/${eventId}/status`, { status })
|
||||
};
|
||||
|
||||
export const authApi = {
|
||||
me: () => api.get<any>('/auth/me'),
|
||||
logout: () => api.post<void>('/auth/logout'),
|
||||
setup: () => api.get<any>('/auth/setup'),
|
||||
googleCallback: (code: string) => api.post<any>('/auth/google/callback', { code })
|
||||
};
|
||||
Reference in New Issue
Block a user