Initial commit
This commit is contained in:
@@ -0,0 +1,16 @@
|
||||
# frontend/src/api
|
||||
|
||||
## OVERVIEW
|
||||
|
||||
API client for backend communication.
|
||||
|
||||
## WHERE TO LOOK
|
||||
|
||||
| File | Purpose |
|
||||
|------|---------|
|
||||
| `client.ts` | Fetch client setup |
|
||||
|
||||
## CONVENTIONS
|
||||
|
||||
- TanStack Query hooks for data fetching
|
||||
- Types from `../types`
|
||||
@@ -0,0 +1,100 @@
|
||||
import type { SleepSessionCreate, SleepSessionUpdate, SleepSessionRead, SessionListResponse } from '@/types';
|
||||
|
||||
const BASE_URL = import.meta.env.VITE_API_BASE_URL || '';
|
||||
|
||||
export function localToUTC(localValue: string): string {
|
||||
return localValue;
|
||||
}
|
||||
|
||||
export async function fetchActiveSession(): Promise<SleepSessionRead | null> {
|
||||
const response = await fetch(`${BASE_URL}/api/sessions/active`);
|
||||
if (!response.ok) throw new Error('Failed to fetch active session');
|
||||
const data = await response.json();
|
||||
return data.session;
|
||||
}
|
||||
|
||||
export async function fetchSessions(from_date?: string, to_date?: string, limit: number = 200): Promise<SessionListResponse> {
|
||||
const params = new URLSearchParams();
|
||||
if (from_date) params.append('from_date', from_date);
|
||||
if (to_date) params.append('to_date', to_date);
|
||||
if (limit) params.append('limit', limit.toString());
|
||||
|
||||
const response = await fetch(`${BASE_URL}/api/sessions?${params.toString()}`);
|
||||
if (!response.ok) throw new Error('Failed to fetch sessions');
|
||||
return response.json();
|
||||
}
|
||||
|
||||
export async function createSession(payload: SleepSessionCreate): Promise<SleepSessionRead> {
|
||||
const utcTime = localToUTC(payload.start_time);
|
||||
const response = await fetch(`${BASE_URL}/api/sessions`, {
|
||||
method: 'POST',
|
||||
headers: { 'Content-Type': 'application/json' },
|
||||
body: JSON.stringify({ start_time: utcTime }),
|
||||
});
|
||||
if (!response.ok) {
|
||||
const errorData = await response.json();
|
||||
throw new Error(errorData.detail || 'Failed to create session');
|
||||
}
|
||||
return response.json();
|
||||
}
|
||||
|
||||
export async function endSession(sessionId: number, payload: SleepSessionUpdate): Promise<SleepSessionRead> {
|
||||
const utcTime = payload.end_time ? localToUTC(payload.end_time) : undefined;
|
||||
const response = await fetch(`${BASE_URL}/api/sessions/${sessionId}/end`, {
|
||||
method: 'PATCH',
|
||||
headers: { 'Content-Type': 'application/json' },
|
||||
body: JSON.stringify({ end_time: utcTime }),
|
||||
});
|
||||
if (!response.ok) {
|
||||
const errorData = await response.json();
|
||||
throw new Error(errorData.detail || 'Failed to end session');
|
||||
}
|
||||
return response.json();
|
||||
}
|
||||
|
||||
export async function updateSession(sessionId: number, payload: SleepSessionUpdate): Promise<SleepSessionRead> {
|
||||
const response = await fetch(`${BASE_URL}/api/sessions/${sessionId}`, {
|
||||
method: 'PUT',
|
||||
headers: { 'Content-Type': 'application/json' },
|
||||
body: JSON.stringify(payload),
|
||||
});
|
||||
if (!response.ok) {
|
||||
const errorData = await response.json();
|
||||
throw new Error(errorData.detail || 'Failed to update session');
|
||||
}
|
||||
return response.json();
|
||||
}
|
||||
|
||||
export async function deleteSession(sessionId: number): Promise<void> {
|
||||
const response = await fetch(`${BASE_URL}/api/sessions/${sessionId}`, {
|
||||
method: 'DELETE',
|
||||
});
|
||||
if (!response.ok) throw new Error('Failed to delete session');
|
||||
}
|
||||
|
||||
export async function fetchDailySummary(from_date: string, to_date: string, day_start: string, day_end: string): Promise<any> {
|
||||
const fromDT = from_date + 'T00:00:00';
|
||||
const toDT = to_date + 'T23:59:59';
|
||||
const params = new URLSearchParams({ from_date: fromDT, to_date: toDT, day_start, day_end });
|
||||
const response = await fetch(`${BASE_URL}/api/stats/daily-summary?${params.toString()}`);
|
||||
if (!response.ok) throw new Error('Failed to fetch daily summary');
|
||||
return response.json();
|
||||
}
|
||||
|
||||
export async function fetchTimetable(from_date: string, to_date: string, day_start: string, day_end: string): Promise<any> {
|
||||
const fromDT = from_date + 'T00:00:00';
|
||||
const toDT = to_date + 'T23:59:59';
|
||||
const params = new URLSearchParams({ from_date: fromDT, to_date: toDT, day_start, day_end });
|
||||
const response = await fetch(`${BASE_URL}/api/stats/timetable?${params.toString()}`);
|
||||
if (!response.ok) throw new Error('Failed to fetch timetable');
|
||||
return response.json();
|
||||
}
|
||||
|
||||
export async function fetchWakeSleepTimes(from_date: string, to_date: string, wakeup_ref: string, bedtime_ref: string): Promise<any> {
|
||||
const fromDT = from_date + 'T00:00:00';
|
||||
const toDT = to_date + 'T23:59:59';
|
||||
const params = new URLSearchParams({ from_date: fromDT, to_date: toDT, wakeup_ref, bedtime_ref });
|
||||
const response = await fetch(`${BASE_URL}/api/stats/wake-sleep-times?${params.toString()}`);
|
||||
if (!response.ok) throw new Error('Failed to fetch wake/sleep times');
|
||||
return response.json();
|
||||
}
|
||||
Reference in New Issue
Block a user