mirror of
https://github.com/mauriceboe/TREK.git
synced 2026-06-22 14:51:45 +00:00
test(front): add test suite frontend (WIP)
This commit is contained in:
@@ -0,0 +1,12 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
|
||||
export const addonHandlers = [
|
||||
http.get('/api/addons', () => {
|
||||
return HttpResponse.json({
|
||||
addons: [
|
||||
{ id: 'vacay', name: 'Vacay', type: 'feature', icon: 'calendar', enabled: true },
|
||||
{ id: 'atlas', name: 'Atlas', type: 'feature', icon: 'map', enabled: true },
|
||||
],
|
||||
});
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,125 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildUser, buildAdmin } from '../../factories';
|
||||
|
||||
export const adminHandlers = [
|
||||
http.get('/api/admin/users', () => {
|
||||
const user1 = buildUser({ username: 'alice', email: 'alice@example.com' });
|
||||
const admin1 = buildAdmin({ username: 'admin', email: 'admin@example.com' });
|
||||
return HttpResponse.json({ users: [admin1, user1] });
|
||||
}),
|
||||
|
||||
http.post('/api/admin/users', async ({ request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const user = buildUser({ ...body });
|
||||
return HttpResponse.json({ user });
|
||||
}),
|
||||
|
||||
http.put('/api/admin/users/:id', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const user = buildUser({ id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ user });
|
||||
}),
|
||||
|
||||
http.delete('/api/admin/users/:id', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.get('/api/admin/stats', () => {
|
||||
return HttpResponse.json({
|
||||
totalUsers: 2,
|
||||
totalTrips: 5,
|
||||
totalPlaces: 42,
|
||||
totalFiles: 8,
|
||||
});
|
||||
}),
|
||||
|
||||
http.get('/api/admin/invites', () => {
|
||||
return HttpResponse.json({ invites: [] });
|
||||
}),
|
||||
|
||||
http.post('/api/admin/invites', async ({ request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
return HttpResponse.json({ invite: { id: 1, token: 'test-invite-token', ...body } });
|
||||
}),
|
||||
|
||||
http.delete('/api/admin/invites/:id', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.get('/api/admin/oidc', () => {
|
||||
return HttpResponse.json({
|
||||
issuer: '',
|
||||
client_id: '',
|
||||
client_secret: '',
|
||||
client_secret_set: false,
|
||||
display_name: '',
|
||||
oidc_only: false,
|
||||
discovery_url: '',
|
||||
});
|
||||
}),
|
||||
|
||||
http.put('/api/admin/oidc', async ({ request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
return HttpResponse.json({ ...body });
|
||||
}),
|
||||
|
||||
http.get('/api/admin/version-check', () => {
|
||||
return HttpResponse.json({ update_available: false, latest: '1.0.0', current: '1.0.0' });
|
||||
}),
|
||||
|
||||
http.get('/api/admin/bag-tracking', () => {
|
||||
return HttpResponse.json({ enabled: false });
|
||||
}),
|
||||
|
||||
http.put('/api/admin/bag-tracking', async ({ request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
return HttpResponse.json({ enabled: body.enabled });
|
||||
}),
|
||||
|
||||
http.get('/api/admin/addons', () => {
|
||||
return HttpResponse.json({ addons: [] });
|
||||
}),
|
||||
|
||||
http.get('/api/admin/packing-templates', () => {
|
||||
return HttpResponse.json({ templates: [] });
|
||||
}),
|
||||
|
||||
http.get('/api/admin/audit-log', () => {
|
||||
return HttpResponse.json({ logs: [], total: 0 });
|
||||
}),
|
||||
|
||||
http.get('/api/admin/mcp-tokens', () => {
|
||||
return HttpResponse.json({ tokens: [] });
|
||||
}),
|
||||
|
||||
http.get('/api/admin/permissions', () => {
|
||||
return HttpResponse.json({ permissions: {} });
|
||||
}),
|
||||
|
||||
http.get('/api/admin/notification-preferences', () => {
|
||||
return HttpResponse.json({
|
||||
event_types: [],
|
||||
available_channels: {},
|
||||
implemented_combos: {},
|
||||
preferences: {},
|
||||
});
|
||||
}),
|
||||
|
||||
// Auth settings endpoints used by AdminPage
|
||||
http.get('/api/auth/app-settings', () => {
|
||||
return HttpResponse.json({});
|
||||
}),
|
||||
|
||||
http.put('/api/auth/app-settings', async ({ request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
return HttpResponse.json({ ...body });
|
||||
}),
|
||||
|
||||
http.get('/api/auth/me/settings', () => {
|
||||
return HttpResponse.json({ settings: { maps_api_key: '', openweather_api_key: '' } });
|
||||
}),
|
||||
|
||||
http.get('/api/auth/validate-keys', () => {
|
||||
return HttpResponse.json({ maps: true, weather: true });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,28 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildAssignment, buildPlace } from '../../factories';
|
||||
|
||||
export const assignmentsHandlers = [
|
||||
http.post('/api/trips/:id/days/:dayId/assignments', async ({ params, request }) => {
|
||||
const body = await request.json() as { place_id: number };
|
||||
const place = buildPlace({ id: body.place_id, trip_id: Number(params.id) });
|
||||
const assignment = buildAssignment({
|
||||
day_id: Number(params.dayId),
|
||||
place_id: body.place_id,
|
||||
place,
|
||||
order_index: 0,
|
||||
});
|
||||
return HttpResponse.json({ assignment });
|
||||
}),
|
||||
|
||||
http.delete('/api/trips/:id/days/:dayId/assignments/:assignmentId', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/days/:dayId/assignments/reorder', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/assignments/:assignmentId/move', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,31 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildUser, buildAppConfig } from '../../factories';
|
||||
|
||||
export const authHandlers = [
|
||||
http.post('/api/auth/login', () => {
|
||||
const user = buildUser();
|
||||
return HttpResponse.json({ user, token: 'mock-token' });
|
||||
}),
|
||||
|
||||
http.get('/api/auth/me', () => {
|
||||
const user = buildUser();
|
||||
return HttpResponse.json({ user });
|
||||
}),
|
||||
|
||||
http.post('/api/auth/register', () => {
|
||||
const user = buildUser();
|
||||
return HttpResponse.json({ user, token: 'mock-token' });
|
||||
}),
|
||||
|
||||
http.get('/api/auth/app-config', () => {
|
||||
return HttpResponse.json(buildAppConfig());
|
||||
}),
|
||||
|
||||
http.post('/api/auth/ws-token', () => {
|
||||
return HttpResponse.json({ token: 'mock-ws-token' });
|
||||
}),
|
||||
|
||||
http.post('/api/auth/logout', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,38 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildBudgetItem } from '../../factories';
|
||||
|
||||
export const budgetHandlers = [
|
||||
http.get('/api/trips/:id/budget', ({ params }) => {
|
||||
return HttpResponse.json({
|
||||
items: [buildBudgetItem({ trip_id: Number(params.id) })],
|
||||
});
|
||||
}),
|
||||
|
||||
http.post('/api/trips/:id/budget', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const item = buildBudgetItem({ trip_id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ item });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/budget/:itemId', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const item = buildBudgetItem({ id: Number(params.itemId), trip_id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ item });
|
||||
}),
|
||||
|
||||
http.delete('/api/trips/:id/budget/:itemId', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/budget/:itemId/members', async ({ params, request }) => {
|
||||
const body = await request.json() as { user_ids: number[] };
|
||||
const members = body.user_ids.map(uid => ({ user_id: uid, paid: false }));
|
||||
const item = buildBudgetItem({ id: Number(params.itemId), trip_id: Number(params.id), persons: body.user_ids.length, members });
|
||||
return HttpResponse.json({ members, item });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/budget/:itemId/members/:userId/paid', async ({ params, request }) => {
|
||||
const body = await request.json() as { paid: boolean };
|
||||
return HttpResponse.json({ success: true, paid: body.paid });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,31 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildDayNote } from '../../factories';
|
||||
|
||||
export const dayNotesHandlers = [
|
||||
http.get('/api/trips/:id/days/:dayId/notes', ({ params }) => {
|
||||
return HttpResponse.json({
|
||||
notes: [buildDayNote({ day_id: Number(params.dayId) })],
|
||||
});
|
||||
}),
|
||||
|
||||
http.post('/api/trips/:id/days/:dayId/notes', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const note = buildDayNote({ day_id: Number(params.dayId), ...body });
|
||||
return HttpResponse.json({ note });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/days/:dayId/notes/:noteId', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const note = buildDayNote({ id: Number(params.noteId), day_id: Number(params.dayId), ...body });
|
||||
return HttpResponse.json({ note });
|
||||
}),
|
||||
|
||||
http.delete('/api/trips/:id/days/:dayId/notes/:noteId', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/days/:dayId', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
return HttpResponse.json({ day: { id: Number(params.dayId), trip_id: Number(params.id), ...body } });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,19 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildTripFile } from '../../factories';
|
||||
|
||||
export const filesHandlers = [
|
||||
http.get('/api/trips/:id/files', ({ params }) => {
|
||||
return HttpResponse.json({
|
||||
files: [buildTripFile({ trip_id: Number(params.id) })],
|
||||
});
|
||||
}),
|
||||
|
||||
http.post('/api/trips/:id/files', ({ params }) => {
|
||||
const file = buildTripFile({ trip_id: Number(params.id) });
|
||||
return HttpResponse.json({ file });
|
||||
}),
|
||||
|
||||
http.delete('/api/trips/:id/files/:fileId', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,37 @@
|
||||
import { authHandlers } from './auth';
|
||||
import { settingsHandlers } from './settings';
|
||||
import { addonHandlers } from './addons';
|
||||
import { notificationHandlers } from './notifications';
|
||||
import { vacayHandlers } from './vacay';
|
||||
import { tripsHandlers } from './trips';
|
||||
import { placesHandlers } from './places';
|
||||
import { assignmentsHandlers } from './assignments';
|
||||
import { packingHandlers } from './packing';
|
||||
import { todoHandlers } from './todo';
|
||||
import { budgetHandlers } from './budget';
|
||||
import { reservationsHandlers } from './reservations';
|
||||
import { filesHandlers } from './files';
|
||||
import { tagsHandlers } from './tags';
|
||||
import { dayNotesHandlers } from './dayNotes';
|
||||
import { adminHandlers } from './admin';
|
||||
import { sharedHandlers } from './shared';
|
||||
|
||||
export const defaultHandlers = [
|
||||
...authHandlers,
|
||||
...settingsHandlers,
|
||||
...addonHandlers,
|
||||
...notificationHandlers,
|
||||
...vacayHandlers,
|
||||
...tripsHandlers,
|
||||
...placesHandlers,
|
||||
...assignmentsHandlers,
|
||||
...packingHandlers,
|
||||
...todoHandlers,
|
||||
...budgetHandlers,
|
||||
...reservationsHandlers,
|
||||
...filesHandlers,
|
||||
...tagsHandlers,
|
||||
...dayNotesHandlers,
|
||||
...adminHandlers,
|
||||
...sharedHandlers,
|
||||
];
|
||||
@@ -0,0 +1,90 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
|
||||
export const notificationHandlers = [
|
||||
http.get('/api/notifications/in-app', ({ request }) => {
|
||||
const url = new URL(request.url);
|
||||
const offset = parseInt(url.searchParams.get('offset') || '0', 10);
|
||||
const limit = parseInt(url.searchParams.get('limit') || '20', 10);
|
||||
|
||||
const allNotifications = Array.from({ length: 25 }, (_, i) => ({
|
||||
id: i + 1,
|
||||
type: 'simple',
|
||||
scope: 'trip',
|
||||
target: 1,
|
||||
sender_id: 2,
|
||||
sender_username: 'alice',
|
||||
sender_avatar: null,
|
||||
recipient_id: 1,
|
||||
title_key: 'notif.title',
|
||||
title_params: '{}',
|
||||
text_key: 'notif.text',
|
||||
text_params: '{}',
|
||||
positive_text_key: null,
|
||||
negative_text_key: null,
|
||||
response: null,
|
||||
navigate_text_key: null,
|
||||
navigate_target: null,
|
||||
is_read: i < 5 ? 0 : 1,
|
||||
created_at: '2025-01-01T00:00:00.000Z',
|
||||
}));
|
||||
|
||||
const page = allNotifications.slice(offset, offset + limit);
|
||||
|
||||
return HttpResponse.json({
|
||||
notifications: page,
|
||||
total: allNotifications.length,
|
||||
unread_count: 5,
|
||||
});
|
||||
}),
|
||||
|
||||
http.get('/api/notifications/in-app/unread-count', () => {
|
||||
return HttpResponse.json({ count: 5 });
|
||||
}),
|
||||
|
||||
http.put('/api/notifications/in-app/:id/read', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.put('/api/notifications/in-app/:id/unread', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.put('/api/notifications/in-app/read-all', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.delete('/api/notifications/in-app/:id', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.delete('/api/notifications/in-app/all', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.post('/api/notifications/in-app/:id/respond', async ({ request, params }) => {
|
||||
const body = await request.json() as { response: string };
|
||||
return HttpResponse.json({
|
||||
notification: {
|
||||
id: Number(params.id),
|
||||
type: 'boolean',
|
||||
scope: 'trip',
|
||||
target: 1,
|
||||
sender_id: 2,
|
||||
sender_username: 'alice',
|
||||
sender_avatar: null,
|
||||
recipient_id: 1,
|
||||
title_key: 'notif.title',
|
||||
title_params: '{}',
|
||||
text_key: 'notif.text',
|
||||
text_params: '{}',
|
||||
positive_text_key: 'accept',
|
||||
negative_text_key: 'decline',
|
||||
response: body.response,
|
||||
navigate_text_key: null,
|
||||
navigate_target: null,
|
||||
is_read: 1,
|
||||
created_at: '2025-01-01T00:00:00.000Z',
|
||||
},
|
||||
});
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,26 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildPackingItem } from '../../factories';
|
||||
|
||||
export const packingHandlers = [
|
||||
http.get('/api/trips/:id/packing', ({ params }) => {
|
||||
return HttpResponse.json({
|
||||
items: [buildPackingItem({ trip_id: Number(params.id) })],
|
||||
});
|
||||
}),
|
||||
|
||||
http.post('/api/trips/:id/packing', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const item = buildPackingItem({ trip_id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ item });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/packing/:itemId', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const item = buildPackingItem({ id: Number(params.itemId), trip_id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ item });
|
||||
}),
|
||||
|
||||
http.delete('/api/trips/:id/packing/:itemId', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,25 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildPlace } from '../../factories';
|
||||
|
||||
export const placesHandlers = [
|
||||
http.get('/api/trips/:id/places', ({ params }) => {
|
||||
const tripId = Number(params.id);
|
||||
return HttpResponse.json({ places: [buildPlace({ trip_id: tripId }), buildPlace({ trip_id: tripId })] });
|
||||
}),
|
||||
|
||||
http.post('/api/trips/:id/places', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const place = buildPlace({ trip_id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ place });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/places/:placeId', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const place = buildPlace({ id: Number(params.placeId), trip_id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ place });
|
||||
}),
|
||||
|
||||
http.delete('/api/trips/:id/places/:placeId', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,30 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildReservation } from '../../factories';
|
||||
|
||||
export const reservationsHandlers = [
|
||||
http.get('/api/trips/:id/reservations', ({ params }) => {
|
||||
return HttpResponse.json({
|
||||
reservations: [buildReservation({ trip_id: Number(params.id) })],
|
||||
});
|
||||
}),
|
||||
|
||||
http.post('/api/trips/:id/reservations', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const reservation = buildReservation({ trip_id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ reservation });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/reservations/:reservationId', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const reservation = buildReservation({
|
||||
id: Number(params.reservationId),
|
||||
trip_id: Number(params.id),
|
||||
...body,
|
||||
});
|
||||
return HttpResponse.json({ reservation });
|
||||
}),
|
||||
|
||||
http.delete('/api/trips/:id/reservations/:reservationId', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,16 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildSettings } from '../../factories';
|
||||
|
||||
export const settingsHandlers = [
|
||||
http.get('/api/settings', () => {
|
||||
return HttpResponse.json({ settings: buildSettings() });
|
||||
}),
|
||||
|
||||
http.put('/api/settings', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.post('/api/settings/bulk', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,36 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildTrip, buildDay, buildPlace } from '../../factories';
|
||||
|
||||
export const sharedHandlers = [
|
||||
http.get('/api/shared/:token', ({ params }) => {
|
||||
const { token } = params;
|
||||
|
||||
if (token === 'invalid-token' || token === 'expired-token') {
|
||||
return new HttpResponse(null, { status: 404 });
|
||||
}
|
||||
|
||||
const trip = { ...buildTrip({ start_date: '2026-07-01', end_date: '2026-07-05' }), title: 'Shared Paris Trip' };
|
||||
const day1 = buildDay({ trip_id: trip.id, date: '2026-07-01' });
|
||||
const place1 = buildPlace({ trip_id: trip.id, name: 'Eiffel Tower', lat: 48.8584, lng: 2.2945 });
|
||||
|
||||
return HttpResponse.json({
|
||||
trip,
|
||||
days: [day1],
|
||||
assignments: {},
|
||||
dayNotes: {},
|
||||
places: [place1],
|
||||
reservations: [],
|
||||
accommodations: [],
|
||||
packing: [],
|
||||
budget: [],
|
||||
categories: [],
|
||||
permissions: {
|
||||
share_bookings: true,
|
||||
share_packing: false,
|
||||
share_budget: false,
|
||||
share_collab: false,
|
||||
},
|
||||
collab: [],
|
||||
});
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,24 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildTag, buildCategory } from '../../factories';
|
||||
|
||||
export const tagsHandlers = [
|
||||
http.get('/api/tags', () => {
|
||||
return HttpResponse.json({ tags: [buildTag(), buildTag()] });
|
||||
}),
|
||||
|
||||
http.post('/api/tags', async ({ request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const tag = buildTag(body);
|
||||
return HttpResponse.json({ tag });
|
||||
}),
|
||||
|
||||
http.get('/api/categories', () => {
|
||||
return HttpResponse.json({ categories: [buildCategory(), buildCategory()] });
|
||||
}),
|
||||
|
||||
http.post('/api/categories', async ({ request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const category = buildCategory(body);
|
||||
return HttpResponse.json({ category });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,26 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildTodoItem } from '../../factories';
|
||||
|
||||
export const todoHandlers = [
|
||||
http.get('/api/trips/:id/todo', ({ params }) => {
|
||||
return HttpResponse.json({
|
||||
items: [buildTodoItem({ trip_id: Number(params.id) })],
|
||||
});
|
||||
}),
|
||||
|
||||
http.post('/api/trips/:id/todo', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const item = buildTodoItem({ trip_id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ item });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id/todo/:itemId', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const item = buildTodoItem({ id: Number(params.itemId), trip_id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ item });
|
||||
}),
|
||||
|
||||
http.delete('/api/trips/:id/todo/:itemId', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,49 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
import { buildTrip, buildDay, buildUser } from '../../factories';
|
||||
|
||||
export const tripsHandlers = [
|
||||
// List all trips (active or archived)
|
||||
http.get('/api/trips', ({ request }) => {
|
||||
const url = new URL(request.url);
|
||||
const archived = url.searchParams.get('archived');
|
||||
if (archived) {
|
||||
return HttpResponse.json({ trips: [] });
|
||||
}
|
||||
const trip1 = buildTrip({ title: 'Paris Adventure', start_date: '2026-07-01', end_date: '2026-07-10' });
|
||||
const trip2 = buildTrip({ title: 'Tokyo Trip', start_date: '2026-09-01', end_date: '2026-09-15' });
|
||||
return HttpResponse.json({ trips: [trip1, trip2] });
|
||||
}),
|
||||
|
||||
http.get('/api/trips/:id', ({ params }) => {
|
||||
const trip = buildTrip({ id: Number(params.id) });
|
||||
return HttpResponse.json({ trip });
|
||||
}),
|
||||
|
||||
http.get('/api/trips/:id/days', ({ params }) => {
|
||||
const tripId = Number(params.id);
|
||||
const day1 = buildDay({ trip_id: tripId, assignments: [], notes_items: [] });
|
||||
const day2 = buildDay({ trip_id: tripId, assignments: [], notes_items: [] });
|
||||
return HttpResponse.json({ days: [day1, day2] });
|
||||
}),
|
||||
|
||||
http.put('/api/trips/:id', async ({ params, request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const trip = buildTrip({ id: Number(params.id), ...body });
|
||||
return HttpResponse.json({ trip });
|
||||
}),
|
||||
|
||||
http.post('/api/trips', async ({ request }) => {
|
||||
const body = await request.json() as Record<string, unknown>;
|
||||
const trip = buildTrip({ ...body });
|
||||
return HttpResponse.json({ trip });
|
||||
}),
|
||||
|
||||
http.get('/api/trips/:id/members', ({ params }) => {
|
||||
const owner = buildUser();
|
||||
return HttpResponse.json({ owner, members: [] });
|
||||
}),
|
||||
|
||||
http.get('/api/trips/:id/accommodations', () => {
|
||||
return HttpResponse.json({ accommodations: [] });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,127 @@
|
||||
import { http, HttpResponse } from 'msw';
|
||||
|
||||
export const vacayHandlers = [
|
||||
http.get('/api/addons/vacay/plan', () => {
|
||||
return HttpResponse.json({
|
||||
plan: {
|
||||
id: 1,
|
||||
holidays_enabled: false,
|
||||
holidays_region: null,
|
||||
holiday_calendars: [],
|
||||
block_weekends: true,
|
||||
carry_over_enabled: false,
|
||||
company_holidays_enabled: false,
|
||||
},
|
||||
users: [{ id: 1, username: 'user1', color: '#3b82f6' }],
|
||||
pendingInvites: [],
|
||||
incomingInvites: [],
|
||||
isOwner: true,
|
||||
isFused: false,
|
||||
});
|
||||
}),
|
||||
|
||||
http.put('/api/addons/vacay/plan', () => {
|
||||
return HttpResponse.json({
|
||||
plan: {
|
||||
id: 1,
|
||||
holidays_enabled: true,
|
||||
holidays_region: null,
|
||||
holiday_calendars: [],
|
||||
block_weekends: true,
|
||||
carry_over_enabled: false,
|
||||
company_holidays_enabled: false,
|
||||
},
|
||||
});
|
||||
}),
|
||||
|
||||
http.get('/api/addons/vacay/years', () => {
|
||||
return HttpResponse.json({ years: [2025, 2026] });
|
||||
}),
|
||||
|
||||
http.post('/api/addons/vacay/years', () => {
|
||||
return HttpResponse.json({ years: [2025, 2026, 2027] });
|
||||
}),
|
||||
|
||||
http.delete('/api/addons/vacay/years/:year', () => {
|
||||
return HttpResponse.json({ years: [2025] });
|
||||
}),
|
||||
|
||||
http.get('/api/addons/vacay/entries/:year', () => {
|
||||
return HttpResponse.json({
|
||||
entries: [
|
||||
{ date: '2025-06-15', user_id: 1 },
|
||||
{ date: '2025-06-16', user_id: 1 },
|
||||
],
|
||||
companyHolidays: [],
|
||||
});
|
||||
}),
|
||||
|
||||
http.post('/api/addons/vacay/entries/toggle', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.post('/api/addons/vacay/entries/company-holiday', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.get('/api/addons/vacay/stats/:year', () => {
|
||||
return HttpResponse.json({
|
||||
stats: [{ user_id: 1, vacation_days: 30, used: 2 }],
|
||||
});
|
||||
}),
|
||||
|
||||
http.put('/api/addons/vacay/stats/:year', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.get('/api/addons/vacay/holidays/countries', () => {
|
||||
return HttpResponse.json({ countries: ['DE', 'US', 'FR'] });
|
||||
}),
|
||||
|
||||
http.get('/api/addons/vacay/holidays/:year/:country', () => {
|
||||
return HttpResponse.json([
|
||||
{ date: '2025-12-25', name: 'Christmas', localName: 'Weihnachten', global: true, counties: null },
|
||||
{ date: '2025-01-01', name: 'New Year', localName: 'Neujahr', global: true, counties: null },
|
||||
]);
|
||||
}),
|
||||
|
||||
http.put('/api/addons/vacay/color', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.post('/api/addons/vacay/invite', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.post('/api/addons/vacay/invite/accept', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.post('/api/addons/vacay/invite/decline', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.post('/api/addons/vacay/invite/cancel', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.post('/api/addons/vacay/dissolve', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
|
||||
http.post('/api/addons/vacay/plan/holiday-calendars', () => {
|
||||
return HttpResponse.json({
|
||||
calendar: { id: 1, plan_id: 1, region: 'DE', label: null, color: '#ef4444', sort_order: 0 },
|
||||
});
|
||||
}),
|
||||
|
||||
http.put('/api/addons/vacay/plan/holiday-calendars/:id', () => {
|
||||
return HttpResponse.json({
|
||||
calendar: { id: 1, plan_id: 1, region: 'US', label: 'US Holidays', color: '#3b82f6', sort_order: 0 },
|
||||
});
|
||||
}),
|
||||
|
||||
http.delete('/api/addons/vacay/plan/holiday-calendars/:id', () => {
|
||||
return HttpResponse.json({ success: true });
|
||||
}),
|
||||
];
|
||||
@@ -0,0 +1,4 @@
|
||||
import { setupServer } from 'msw/node';
|
||||
import { defaultHandlers } from './handlers';
|
||||
|
||||
export const server = setupServer(...defaultHandlers);
|
||||
Reference in New Issue
Block a user