Back to writing
June 15, 20218 min readArchitecture

Using C4 Diagrams In Security Work

A practical way to use C4 diagrams for trust boundaries, data flows, and incident response.

By Kevin O'Connor

Using C4 Diagrams In Security Work

The worst time to discover bad architecture documentation is during an incident.

Someone asks which systems are exposed, where customer data flows, or what can talk to the affected database. The answer is a diagram nobody trusts, a wiki page from two reorganizations ago, and a Slack thread full of guesses.

The C4 model helps because it gives teams four levels of zoom:

  1. Context - what the system talks to
  2. Container - the major deployable pieces
  3. Component - the important parts inside a container
  4. Code - implementation details, when they are actually useful

Security work usually lives in the first three.

Context: What Is Outside The System?

A context diagram should answer basic questions quickly:

  • Who uses the system?
  • Which external systems does it depend on?
  • What data crosses the boundary?
  • Which connections are untrusted, semi-trusted, or internal?

Example:

[Customer] --HTTPS--> [E-commerce Platform] --API--> [Payment Processor]
                              |
                              v
                       [Inventory System]

For security review, I would annotate:

  • customer PII enters from the public internet
  • payment data leaves to a third party
  • inventory is an internal dependency
  • authentication and logging are required at the platform boundary

That is enough to start a useful conversation.

Container: What Are The Big Pieces?

A container diagram shows the major running parts: web app, API, database, queue, storage, identity provider, load balancer, and so on.

Example:

[Browser] --TLS--> [Load Balancer] --HTTP--> [Web App]
                                             |
                                             v
                                      [API Service] --SQL--> [Database]
                                             |
                                             v
                                      [Object Storage]

This version immediately raises questions:

  • Why is traffic from the load balancer to the web app HTTP?
  • Which component validates identity?
  • Does the API have direct database access?
  • What is logged before object storage reads and writes?
  • Where is the trust boundary between public and private networks?

The point is not to make the diagram pretty. The point is to make hidden assumptions visible.

Component: Where Do Security Decisions Happen?

Component diagrams are useful when a container owns meaningful security logic.

Example:

[Request Handler] --> [Authentication] --> [Authorization] --> [Business Logic]
                             |                    |                    |
                             v                    v                    v
                       [User Store]          [Policy Store]       [Audit Logger]

Now the review can get specific:

  • Are authentication and authorization separate?
  • Is policy cached, and if so, how is it invalidated?
  • Does the audit logger see denied actions or only successful ones?
  • Can business logic bypass the authorization layer?

This is where architecture documentation starts helping code review.

Code: Use Sparingly

Most security teams do not need class diagrams for everything. Code-level diagrams are useful when the implementation pattern matters:

  • cryptographic wrappers
  • authorization decorators
  • policy evaluation paths
  • serialization and validation boundaries
  • high-risk parsing logic

If the diagram cannot guide a review or explain a failure mode, skip it.

Security Annotations I Actually Use

I keep the notation simple:

  • Red: external or untrusted
  • Yellow: partner or semi-trusted
  • Green: internal service
  • Blue: security control
  • Dashed line: trust boundary
  • Label on flow: protocol plus data classification

For example:

[Partner API] --TLS, contract data--> [API Gateway] --mTLS, internal--> [Order Service]
                 untrusted boundary ^

The exact colors do not matter. Consistency matters.

Where C4 Helps Security Teams

Threat Modeling

Start with the context diagram to find attack surfaces. Use the container diagram to find trust boundaries. Use the component diagram to identify authorization, validation, and logging paths.

That prevents threat modeling from becoming a free-form brainstorm detached from the real system.

Incident Response

During an incident, a current C4 diagram helps answer:

  • what might be affected?
  • what can the compromised system reach?
  • where should logs exist?
  • which dependency could explain the observed behavior?
  • what can be isolated without breaking everything?

Compliance

C4 diagrams are not compliance artifacts by themselves, but they make compliance evidence easier to explain:

  • PCI boundaries
  • PHI flows
  • data retention systems
  • third-party processors
  • audit logging paths

Common Mistakes

  • drawing every database table on a container diagram
  • mixing deployment detail with business context
  • leaving data classification off the flows
  • making one perfect diagram instead of three useful ones
  • letting diagrams age without tying them to reviews or incidents

A Simple Starting Point

Pick one important system and make three diagrams:

  1. context diagram with users, external dependencies, and trust boundaries
  2. container diagram with deployable parts and data stores
  3. component diagram for the part that makes access decisions

Review them with a developer, an operator, and a security person. If all three groups correct the diagram, it is doing its job.

Good security starts with knowing what exists. C4 is one clean way to get there.

Get the next one

New research, sent when there is something worth saying.

In-depth notes on AI security, threat research, and practical defensive work.

Newsletter provider is not connected yet; this opens an email draft.