| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
| Name | Name | Last commit date | ||
|---|---|---|---|---|
A full-stack appointment booking platform built with Next.js, TypeScript, and Supabase with comprehensive testing and role-based access control.
Go to supabase.com, sign in, and create a new project. Once ready:
Place the .env file in the root directory:
NEXT_PUBLIC_SUPABASE_URL=your_supabase_url
NEXT_PUBLIC_SUPABASE_ANON_KEY=your_anon_key
SUPABASE_SERVICE_ROLE_KEY=your_service_role_keynpm install
npm run seed # Creates users, admin, slots, and sample appointment
npm run dev # Start dev servernpm test # Run all tests
npm run test:unit # Unit tests only
npm run test:integration # Integration tests only┌─────────────────────────────────────────────────────────────┐
│ Next.js Frontend │
├──────────────────┬──────────────────┬──────────────────────┤
│ Patient Login │ Doctor Login │ Admin Login │
│ Book/Cancel │ Mark Done │ View All Appts │
└──────────────────┴──────────────────┴──────────────────────┘
│ │ │
├────────────────┼────────────────────┤
▼ ▼ ▼
┌────────────────────────────────────────────────────┐
│ API Routes (Next.js) │
├────────────────────────────────────────────────────┤
│ POST /api/appointments/book │
│ POST /api/appointments/cancel │
│ POST /api/admin/login │
└────────────────────────────────────────────────────┘
│
▼
┌────────────────────────────────────────────────────┐
│ Supabase (PostgreSQL + Auth) │
├────────────────────────────────────────────────────┤
│ • Row-Level Security (RLS) Policies │
│ • RPC Functions with SECURITY DEFINER │
│ • Database Constraints & Indexes │
└────────────────────────────────────────────────────┘
| Method | Endpoint | Authentication | Description |
|---|---|---|---|
| POST | /api/admin/login | None | Authenticates system admin and sets session cookie. |
| POST | /api/appointments/book | Bearer Token | Books an appointment for a patient. |
| POST | /api/appointments/cancel | Bearer Token | Cancels or completes an appointment. |
POST /api/appointments/book
Authentication: Bearer Token (Required)
Request Body:
{
"slotId": "uuid",
"doctorId": "uuid"
}Response (201 Created):
{
"id": "uuid",
"patient_id": "uuid",
"doctor_id": "uuid",
"slot_id": "uuid",
"status": "active",
"created_at": "2026-04-29T10:00:00Z"
}Error Responses:
Business Rules:
POST /api/appointments/cancel
Authentication: Bearer Token (Required)
Request Body:
{
"appointmentId": "uuid",
"action": "cancel" | "done"
}Response (200 OK):
{
"id": "uuid",
"patient_id": "uuid",
"doctor_id": "uuid",
"slot_id": "uuid",
"status": "cancelled" | "done",
"created_at": "2026-04-29T10:00:00Z"
}Business Rules:
Role-Based Access:
| Role | Can Cancel | Can Mark Done | 1-Hour Rule |
|---|---|---|---|
| Patient | Yes (>1hr) | No | Yes |
| Doctor | Yes | Yes | No |
POST /api/admin/login
Authentication: None (Public)
Request Body:
{
"email": "admin@test.com",
"password": "admin123"
}Response (200 OK):
{
"success": true
}Sets admin_session cookie: admin_<adminId> (httpOnly, 24-hour expiry)
Error Responses:
sequenceDiagram
Patient->>UI: Enter slot & doctor
UI->>API: POST /api/appointments/book<br/>Authorization: Bearer token
API->>API: Validate token & user
API->>DB: Fetch slot details
API->>API: Validate slot available
API->>API: Validate slot in future
API->>API: Validate no duplicate booking
API->>DB: RPC book_appointment()
DB->>DB: Lock slot FOR UPDATE
DB->>DB: Verify slot available
DB->>DB: Update slot is_booked=true
DB->>DB: Insert appointment
DB-->>API: Return appointment
API-->>UI: 201 Created + appointment
UI->>UI: Show success & refresh
sequenceDiagram
User->>UI: Click cancel appointment
UI->>API: POST /api/appointments/cancel<br/>Authorization: Bearer token
API->>API: Validate token & user
API->>DB: Fetch appointment
API->>API: Check authorization (owner)
API->>DB: Fetch slot details
API->>API: Validate appointment cancellable
API->>API: Check cancellation window (if patient)
DB->>DB: Update appointment status='cancelled'
DB->>DB: Update slot is_booked=false
DB-->>API: Return updated appointment
API-->>UI: 200 OK + updated status
UI->>UI: Show success & refresh
sequenceDiagram
Admin->>UI: Visit /admin/dashboard
UI->>UI: Check admin_session cookie
UI->>DB: Fetch all appointments (server-side)
DB->>DB: Apply RLS policies
DB-->>UI: Return appointments
UI->>UI: Render table
| Role | Password | |
|---|---|---|
| Doctor 1 | doctor1@test.com | doctor123 |
| Doctor 2 | doctor2@test.com | doctor123 |
| Doctor 3 | doctor3@test.com | doctor123 |
| Patient 1 | patient1@test.com | patient123 |
| Patient 2 | patient2@test.com | patient123 |
| Patient 3 | patient3@test.com | patient123 |
| Admin | admin@test.com | admin123 |
├── app/ │ ├── api/ │ │ ├── admin/login/ # Admin authentication │ │ └── appointments/ │ │ ├── book/ # Booking endpoint │ │ └── cancel/ # Cancellation endpoint │ ├── admin/ │ │ ├── dashboard/ # Admin dashboard (SSR) │ │ └── login/ # Admin login page │ ├── doctor/dashboard/ # Doctor portal │ ├── patient/dashboard/ # Patient portal │ └── layout.tsx ├── lib/ │ ├── supabase.ts # Client Supabase │ ├── supabaseAdmin.ts # Admin Supabase │ └── validators.ts # Business logic ├── tests/ │ ├── unit/validators.test.ts │ ├── integration/ │ │ ├── booking.test.ts │ │ ├── cancellation.test.ts │ │ └── guards.test.ts ├── schema.sql # Database schema └── seed.mjs # Database seeding
| Back | FazBrowse Home | New Git URL |