Next.js App Router + TypeScript + Tailwind + Supabase (Auth + Postgres + Storage).
Create .env.local in project root:
NEXT_PUBLIC_SUPABASE_URL=your_supabase_project_url
NEXT_PUBLIC_SUPABASE_ANON_KEY=your_supabase_anon_key
SUPABASE_SERVICE_ROLE_KEY=your_supabase_service_role_key
NEXT_PUBLIC_APP_URL=http://localhost:3000Notes:
SUPABASE_SERVICE_ROLE_KEYis required for admin-provisioned user invites and status management.- Keep service role key server-side only.
- Configure SMTP in Supabase Auth settings so invite emails are delivered.
npm install
npm run devOpen http://localhost:3000.
- Open Supabase Dashboard -> SQL Editor.
- Run
supabase/migrations/001_init.sql.
This migration creates:
- Tables:
profiles,uploads,upload_locations,audit_logs profileslifecycle fields:status,invited_at,activated_at,created_by,department- Trigger for profile row creation from
auth.users - RLS policies for user/admin access
- Private storage bucket
workdocswith object policies
/authis login-only (no public registration).- Admins invite users from
/admin/users. - Employee receives invite email and completes setup on
/invite. - Account status lifecycle:
invited->activeorsuspended.
Suspended users:
- Cannot proceed through login/dashboard flows.
- See a clear suspension message.
Route: /admin/users
Features:
- List all users from
profiles - Create invite (
email,full_name, optionaldepartment) - Resend invite email
- Activate or suspend user
Route: /admin/audit
Features:
- View recent audit entries from
audit_logs - Filter by action and free-text search
- Inspect actor, IP, target upload, and JSON details
Run in Supabase SQL Editor:
update public.profiles
set role = 'admin', status = 'active', activated_at = now()
where email = 'admin@yourcompany.com';/dashboard: upload file + metadata + GPS/IP evidence/admin: all uploads with uploader and location evidence/uploads/[id]: upload details with secure download
Admin /admin includes:
- Date range filter:
All time,Today,Last 7 days,Last 30 days - CSV export endpoint honoring active filters
- Log in as admin.
- Open
/admin/users. - Create invite for an employee email.
- Open invite email link (
/invite?...). - Set password and profile details.
- Confirm redirect to
/dashboardand status updates toactive.
- In
/admin/users, suspend a user. - Attempt login as suspended user.
- Verify blocked login and suspension message.