feat: implement profile reporting system with admin review

Added comprehensive profile reporting system to allow users to report
inappropriate profiles and admins to review reports.

Features:
- User can report profiles with predefined reasons + custom details
- Duplicate prevention (one pending report per profile per user)
- Rate limiting (5 pending reports maximum per user)
- Admin dashboard to view and filter reports (All, Pending, Reviewed, etc.)
- Admin review modal to update status and add review notes
- Report button on profile page (only visible when viewing others)
- Font Awesome icons for better UI consistency

Database changes:
- New ProfileReport model with ReportReason/ReportStatus enums
- User relations for reports (reportsMade, reportsReceived, reportsReviewed)
- Indices for efficient querying
This commit is contained in:
2026-02-19 18:33:58 -08:00
committed by Naomi Carrigan
parent 5eec4c7640
commit d797d38ddd
9 changed files with 2056 additions and 6 deletions
+44 -4
View File
@@ -201,10 +201,13 @@ model User {
isStaff Boolean @default(false)
createdAt DateTime @default(now())
updatedAt DateTime @updatedAt
comments Comment[]
suggestions Suggestion[]
likes Like[]
refreshTokens RefreshToken[]
comments Comment[]
suggestions Suggestion[]
likes Like[]
refreshTokens RefreshToken[]
reportsMade ProfileReport[] @relation("Reporter")
reportsReceived ProfileReport[] @relation("ReportedUser")
reportsReviewed ProfileReport[] @relation("Reviewer")
@@index([slug], map: "User_slug_key")
}
@@ -329,3 +332,40 @@ model RefreshToken {
@@index([userId])
@@index([expiresAt])
}
enum ReportReason {
INAPPROPRIATE_CONTENT
HARASSMENT
SPAM
IMPERSONATION
OFFENSIVE_NAME
MALICIOUS_LINKS
OTHER
}
enum ReportStatus {
PENDING
REVIEWED
DISMISSED
ACTION_TAKEN
}
model ProfileReport {
id String @id @default(auto()) @map("_id") @db.ObjectId
reportedUserId String @db.ObjectId
reportedUser User @relation("ReportedUser", fields: [reportedUserId], references: [id])
reporterId String @db.ObjectId
reporter User @relation("Reporter", fields: [reporterId], references: [id])
reason ReportReason
details String
status ReportStatus @default(PENDING)
reviewedBy String? @db.ObjectId
reviewer User? @relation("Reviewer", fields: [reviewedBy], references: [id])
reviewNotes String?
createdAt DateTime @default(now())
updatedAt DateTime @updatedAt
@@index([reportedUserId])
@@index([reporterId])
@@index([status])
}