Description
The GET /api/notify?user=<username> endpoint returns the full email address of any registered user to any unauthenticated caller. There is no authentication, authorization, or ownership verification. Anyone who knows (or guesses) a GitHub username can retrieve their private email from the database.
// Anyone can call:
// GET /api/notify?user=octocat
// Response includes the full email:
// { success: true, data: { username: "octocat", email: "user@private.com", frequency: "daily", ... } }
This is a Personally Identifiable Information (PII) leak that could enable targeted phishing, spam, or violate privacy regulations (GDPR, CCPA).
File: app/api/notify/route.ts (GET handler, lines ~80-130)
Note: Issue #2067 covers rate limiting and Zod validation for this endpoint, but does NOT mention the unauthenticated email exposure. This is a distinct security/privacy concern.
Steps to Reproduce
- Register notification preferences via
POST /api/notify with a username and email
- From any browser or tool (no auth needed), call
GET /api/notify?user=<that-username>
- Observe the full email address is returned in the JSON response
- Repeat with any other registered username to harvest emails
Expected Behavior
- The GET endpoint should NOT expose the full email address to unauthenticated callers
- At minimum, the email should be masked (e.g.,
u***r@gm***.com) in unauthenticated responses
- Ideally, reading notification preferences should require some form of ownership verification (e.g., a token sent to the email, or session-based auth)
- The endpoint should only return preference metadata (frequency, flags) without PII
Screenshots / Logs
N/A — this is a logic/design issue, not a visual bug.
Suggested Fix
Option A (Quick fix): Remove the email field from the GET response entirely, or mask it:
return NextResponse.json({
success: true,
message: "Notification preferences fetched successfully.",
data: {
username: notification.username,
email: maskEmail(notification.email), // e.g., "u***@gmail.com"
frequency: notification.frequency,
preferences: { ... },
},
});
Option B (Proper fix): Add authentication — require a secret token (generated on POST and emailed to the user) to read preferences.
Impact
- Security: Any user's email can be enumerated by iterating known GitHub usernames
- Privacy: Violates user expectations and potentially GDPR/CCPA
- Trust: Users registering for notifications don't expect their email to be publicly queryable
Description
The
GET /api/notify?user=<username>endpoint returns the full email address of any registered user to any unauthenticated caller. There is no authentication, authorization, or ownership verification. Anyone who knows (or guesses) a GitHub username can retrieve their private email from the database.This is a Personally Identifiable Information (PII) leak that could enable targeted phishing, spam, or violate privacy regulations (GDPR, CCPA).
File:
app/api/notify/route.ts(GET handler, lines ~80-130)Steps to Reproduce
POST /api/notifywith a username and emailGET /api/notify?user=<that-username>Expected Behavior
u***r@gm***.com) in unauthenticated responsesScreenshots / Logs
N/A — this is a logic/design issue, not a visual bug.
Suggested Fix
Option A (Quick fix): Remove the
emailfield from the GET response entirely, or mask it:Option B (Proper fix): Add authentication — require a secret token (generated on POST and emailed to the user) to read preferences.
Impact