Files
2026-06-16 14:50:09 +05:30

70 lines
2.5 KiB
Markdown

# Prabhupāda Says — Admin
A separate Next.js 16 + Tailwind v4 admin panel that talks to the existing Go
BFF. It reuses the BFF's cookie session (no separate auth system) and every
action is gated server-side by the new `/api/v1/admin/*` endpoints, which
require `role = "admin"`.
## Features
- Email/password login (with the BFF's OTP step when required) + forgot/reset password
- Users — search, paginate, **send a notification** to an individual user
- Posts — search, paginate
- Collections — search, paginate
- Feedback — paginate, filter (all/open/resolved), **reply** (emails the submitter)
- Reports — posts / comments / accounts tabs, search, paginate, **resolve**
## Prerequisites
The BFF must be running with migration `0038_admin_panel` applied (it runs
automatically on BFF startup) and these env vars set **on the BFF**:
```
ADMIN_URL=http://localhost:3001 # this app's origin — added to CORS
# (production: ADMIN_URL=https://admin.prabhupadasays.org)
```
Without `ADMIN_URL`, the browser's credentialed requests from this origin are
blocked by CORS.
## Setup
```bash
cd spsays-admin
cp .env.example .env.local # set NEXT_PUBLIC_BFF_URL
yarn install
yarn dev # http://localhost:3001
```
## Make yourself an admin
The panel only admits users whose role is `admin`. Promote your account once,
directly in Postgres:
```sql
UPDATE users SET role = 'admin' WHERE email = 'you@example.com';
```
Then sign in at `/login` with that account's email + password.
## Production notes
- Deploy on its own subdomain, e.g. `admin.prabhupadasays.org`, and set
`ADMIN_URL` on the BFF to that origin. The session cookie is shared because
the BFF sets it on `.prabhupadasays.org`.
- The app sets `robots: noindex` and should additionally be access-restricted
at the edge if desired — the BFF's `RequireAdmin` is the real security
boundary, but defense in depth doesn't hurt.
## How it maps to the BFF
| Screen | Endpoint |
| ----------- | ------------------------------------------ |
| Login | `POST /auth/login` (+ `verify-login-otp`) |
| Forgot/Reset| `POST /auth/forgot-password` / `reset-password` |
| Users | `GET /admin/users`, `POST /admin/users/{id}/notify` |
| Posts | `GET /admin/posts` |
| Collections | `GET /admin/collections` |
| Feedback | `GET /admin/feedback`, `POST /admin/feedback/{id}/reply` |
| Reports | `GET /admin/reports?type=`, `POST /admin/reports/{type}/{id}/resolve` |