Skip to content
1 min read

Security-first web development

  • #security
  • #web
  • #best-practices

I describe myself as a web developer with a focus on building secure digital experiences. People sometimes assume that means I add a login screen and call it a day. It doesn't. Security-first development is a way of thinking about every decision before you write the code.

Threat-model the boring stuff

Most breaches don't come from exotic exploits. They come from the boring things nobody threat-modelled: a form without rate limiting, a database query built from user input, an environment variable committed by accident.

So I ask three questions about every feature:

  1. What's the worst input someone could send here?
  2. What happens if this request is replayed a thousand times a second?
  3. Who can see this data, and have I actually checked?

Make the safe path the easy path

The trick is to make security the default, so you (and your teammates) have to go out of your way to do the wrong thing.

// Validate everything at the boundary with a schema.
import { z } from "zod";
 
const ContactInput = z.object({
  name: z.string().min(1).max(80),
  email: z.string().email(),
  message: z.string().min(10).max(2000),
});
 
export function parseContact(raw: unknown) {
  return ContactInput.parse(raw); // throws on anything unexpected
}

When validation, escaping and authorization live at the boundary, the rest of your code can trust its inputs. That's not just safer — it's calmer to work in.

It compounds

Every secure habit you build is reusable. The schema you wrote for one form protects the next one. The Content-Security-Policy you tuned once keeps paying off. Security-first isn't slower in the long run — it's how you avoid rewriting everything after the incident.

If you want to talk security, performance or building something properly, get in touch.