5 HIPAA Violations Hiding in Your Next.js Healthcare App Right Now

You shipped your healthcare app. It works. Patients love it. Your security review is next week. Here are five violations I see in almost every Next.js healthcare codebase I review -- and what to do about each one. This is the most common violation I find. Next.js makes it easy to create API routes, and that ease creates a trap: nothing forces you to add authentication. The problem: // app/api/patients/[id]/route.ts export async function GET(req: Request, { params }: { params: { id: string } }) {
You shipped your healthcare app. It works. Patients love it. Your security review is next week.
Here are five violations I see in almost every Next.js healthcare codebase I review -- and what to do about each one.
1. Your API Routes Have No Authentication Middleware
This is the most common violation I find. Next.js makes it easy to create API routes, and that ease creates a trap: nothing forces you to add authentication.
The problem:
// app/api/patients/[id]/route.ts
export async function GET(req: Request, { params }: { params: { id: string } }) {
const patient = await db.patients.findById(params.id);
return Response.json(patient);
}
Enter fullscreen mode Exit fullscreen mode
Anyone with the URL can pull patient records. No token, no session check, nothing. This violates HIPAA 164.312(a)(1) -- the access control standard.
The fix:
// app/api/patients/[id]/route.ts
import { authenticate } from '@/lib/auth';
export async function GET(req: Request, { params }: { params: { id: string } }) {
const user = await authenticate(req);
if (!user) {
return Response.json({ error: 'Unauthorized' }, { status: 401 });
}
// Also check authorization -- can THIS user see THIS patient?
const hasAccess = await checkPatientAccess(user.id, params.id);
if (!hasAccess) {
return Response.json({ error: 'Forbidden' }, { status: 403 });
}
const patient = await db.patients.findById(params.id);
return Response.json(patient);
}
Enter fullscreen mode Exit fullscreen mode
Authentication tells you WHO is asking. Authorization tells you whether they are ALLOWED to see this specific record. You need both.



