Hardcoded user IDs in handlers mean the application is operating as a single-user system dressed up as multi-user software. Every POST, PATCH, or DELETE runs against the demo account's data regardless of which user is authenticated — or whether anyone is authenticated at all. This violates OWASP A01:2021 (Broken Access Control) and CWE-284 (Improper Access Control): the authorization decision has been reduced to a constant. Real users create data they cannot see, and the demo user accumulates all writes silently.
Medium because exploitation requires understanding the application's data model, but any authenticated user can corrupt another user's data or read the demo account's accumulated records.
Pull userId from the authenticated session, not a constant. In every API handler that touches user-scoped data, replace the hardcoded ID with a session lookup:
// Remove this pattern:
const userId = 'demo-user-id'
// Replace with:
import { auth } from '@/lib/auth'
export async function POST(req: Request) {
const session = await auth()
if (!session?.user?.id) {
return Response.json({ error: 'Unauthorized' }, { status: 401 })
}
const userId = session.user.id
// proceed with real userId
}
Search src/app/api/ for string literals matching UUID patterns starting with 0000, 1111, or the literal strings demo-user-id, test-user-1, user-1, and replace every occurrence.
ID: ai-slop-half-finished.hardcoded-test-data.hardcoded-user-id-in-handlers
Severity: medium
What to look for: Walk all API handler files for hardcoded user identifier constants used in data operations. Count all string literals that match these patterns AND are used as arguments to database where, findUnique, findFirst, update, delete, or connect clauses: "demo-user-id", "test-user-1", "user-1", "admin-user", "admin-id", "00000000-0000-0000-0000-000000000000" (nil UUID), "user_demo", UUIDs starting with "11111111-" or "00000000-". Also count assignments like const userId = "demo-user-id" in handlers.
Pass criteria: 0 hardcoded user ID constants are used in handler data operations. Report: "Scanned X API handlers, 0 hardcoded user IDs in data queries."
Fail criteria: At least 1 API handler uses a hardcoded user ID string in a database query or data operation.
Do NOT pass when: The hardcoded ID is only used as a fallback when session lookup fails (still a backdoor into another user's data).
Skip (N/A) when: Project has 0 API handler files.
Detail on fail: "1 hardcoded user ID: 'const userId = \"demo-user-id\"' in app/api/posts/route.ts line 8, used in prisma.post.create({ data: { authorId: userId } })"
Remediation: Hardcoded user IDs mean every user's data gets created under the demo account. Pull the user ID from the actual session:
// Bad: all posts created under demo user
export async function POST(req: Request) {
const userId = "demo-user-id"
const post = await prisma.post.create({ data: { ...body, authorId: userId } })
}
// Good: use the authenticated session
import { auth } from '@/lib/auth'
export async function POST(req: Request) {
const session = await auth()
if (!session?.user) {
return Response.json({ error: 'Unauthorized' }, { status: 401 })
}
const post = await prisma.post.create({ data: { ...body, authorId: session.user.id } })
}