Back to case studies

Compliance · Security

Making infrastructure HIPAA-compliant from the ground up

Health data leaves no room for retrofitting. The cluster went private, the database went private, the path between them never leaves the VPC — and everything around it, from edge filtering to audit logging to a tested recovery plan, was built to hold up under scrutiny.

Technologies

GCP · Private GKE · Cloud SQL · Connect Gateway · Cloud Armor · Cloudflare · Security Command Center · Cloud Audit Logs

Making infrastructure HIPAA-compliant from the ground up architecture diagram

Overview

HIPAA is not a feature you enable. It is a set of obligations about how protected health information is stored, transmitted, accessed, logged, and recovered — and the awkward part is that most of those obligations are about things that are invisible when the application is working correctly. An app can serve traffic perfectly while its database sits on a public IP, its logs quietly capture patient identifiers, and nobody has ever confirmed the backups restore.

So the work went in two directions at once. Inward, everything was closed off: a private GKE cluster, a private database reached only over private IP, storage buckets taken off the public internet with retention policies applied, and deployments routed through GCP's Connect Gateway so that CI could reach a cluster with no public control plane. Outward, the single remaining entry point was hardened in layers — Cloudflare in front of proxied DNS records handling DDoS protection and security rules, with Cloud Armor behind it accepting requests only from Cloudflare's IP ranges.

The rest is the part auditors actually ask about. Security Command Center watches the posture continuously. Audit logging is enabled across the platform and at the database level, with deliberate care taken that no PHI ends up captured in a log line. Disaster recovery was documented and then actually tested against defined RTO and RPO targets rather than assumed. And Business Associate Agreements were signed with both Google and Cloudflare, because a compliant architecture running on a vendor who hasn't agreed to handle PHI is not compliant at all.

The Challenge

Context

The application handled protected health information, which means the infrastructure around it was subject to HIPAA rather than merely benefiting from good practice. That distinction matters: with ordinary hardening you can defer things and catch up later, but here the requirements are external, specific, and evidenced — data has to be encrypted in transit and at rest, access has to be least-privilege and logged, breaches have to be detectable after the fact, recovery objectives have to be defined rather than hoped for, and every vendor touching PHI has to have formally agreed to the responsibility. None of that can be convincingly bolted on after launch, because a large part of what is being demonstrated is that the controls were there the whole time.

Problem Space

Close every path that did not need to exist, harden the one that did, and produce the evidence trail that compliance actually turns on — without leaving the engineering team unable to deploy, debug, or recover. A locked-down environment nobody can operate gets worked around within a month, and the workaround is where the breach comes from.

Approach

The cluster and the database both went private, and the path between them never leaves the VPC. The GKE cluster was made private, so nodes carry no public addresses and the control plane is not exposed to the internet. The database was made private in the same way, and the application connects to it over private IP — which means the traffic carrying PHI travels entirely inside the VPC on Google's network and never traverses the public internet at any point in its life. This is the single highest-value change in the whole engagement. A public database endpoint is a permanent invitation that has to be defended forever with credentials and firewall rules; a private one removes the category of attack rather than mitigating it. Encryption in transit and at rest sits underneath all of this as a baseline, but the network topology is what makes the encryption a second line of defence rather than the only one.

Deployments reach the private cluster through GCP's Connect Gateway. Making a cluster private creates an immediate operational problem: the deployment pipeline can no longer reach it. The usual answers are all bad — a bastion host to maintain and patch, a VPN to manage, a long-lived kubeconfig with cluster credentials sitting in CI, or worst of all, quietly re-opening the control plane to a range of IPs and calling it restricted. Instead, pipelines connect through GCP's Connect Gateway, which brokers authenticated, identity-based access to the private cluster without exposing an endpoint and without static credentials living in the pipeline. Deployments work exactly as before from the engineers' point of view, the cluster stays genuinely private, and access is tied to identity that can be revoked and audited rather than to a secret that can be copied.

The public edge was reduced to one path and then filtered twice. DNS records were proxied through Cloudflare, which handles DDoS protection and enforces security rules at the edge before traffic gets anywhere near the application. On its own that leaves the familiar gap: an attacker who discovers the origin can simply address it directly and skip the edge entirely. Cloud Armor closes that, configured to accept requests only from Cloudflare's published IP ranges, so the origin will not answer anyone who has not come through the front door. Two independent layers, each of which a request must satisfy, and no path into the environment that bypasses both.

Storage was privatized and given the retention it was required to have. Buckets were taken off public access entirely — an unremarkable-sounding change that closes one of the most common ways health data actually leaks, which is not a sophisticated intrusion but an object store that was readable by anyone who guessed the URL. Retention policies were then applied to match what the compliance requirement specified, so data persists for exactly as long as it is supposed to and is not silently deleted early by a lifecycle rule or a well-meaning cleanup script. Retention is one of the requirements teams most often discover they have failed only when someone asks for records that no longer exist.

Audit logging captures everything — deliberately excluding PHI. Audit logging was enabled across the platform and extended down to the database level, so there is a durable record of who accessed what and when, which is precisely the evidence an investigation depends on. The subtlety, and the part that is easy to get wrong, is that logs themselves become a compliance liability the moment they contain protected health information. A query log that records parameter values, an error handler that dumps a request body, a debug statement written during an incident — any of these can turn an audit trail into an unsecured copy of the data it was meant to protect. So logging was configured with explicit care that no PHI is captured in log lines. The result is an audit trail that satisfies the requirement without quietly creating a second, less-protected store of the very data under protection.

Security Command Center watches the posture continuously. A compliant environment on day one drifts. Someone widens a firewall rule to debug an incident, a new bucket is created without the right settings, a service account accumulates permissions it no longer needs. Security Command Center was enabled to monitor the environment continuously and surface misconfigurations and vulnerabilities as they appear, which turns compliance from a state that was true at launch into something observable over time. It also produces the kind of evidence that matters in an assessment: not a claim that the environment is configured correctly, but an ongoing record showing it has been.

Disaster recovery was documented and then actually tested. Recovery objectives were defined explicitly — an RTO for how quickly service must be restored and an RPO for how much data loss is tolerable — and the recovery procedure was written down rather than living in one person's memory. Then it was tested, which is the step that separates a real plan from a document. Testing is where you find out that a backup has been failing silently for weeks, that restoring takes four times longer than assumed, or that the runbook omits a step only the person who built it knew about. Under HIPAA, contingency planning is an explicit requirement rather than a nice-to-have, and an untested plan does not meet it in any meaningful sense.

Business Associate Agreements were signed with Google and Cloudflare. This is the least technical item on the list and one of the most consequential. Under HIPAA, any vendor that stores, transmits, or processes protected health information on your behalf is a business associate and must be under a signed BAA. Without one, the architecture can be flawless and the arrangement is still non-compliant, because the legal chain of responsibility for the data is broken. BAAs were signed with Google, whose infrastructure hosts the workloads and the data, and with Cloudflare, which sits in the request path and therefore handles PHI in transit. Teams routinely get every control right and miss this, usually because it does not look like an infrastructure problem.

Outcomes

  • No public endpoints anywhere — the cluster, the database, and the storage buckets are all private
  • PHI in transit stays inside the VPC on private IP and never traverses the public internet
  • CI deploys into a private cluster via Connect Gateway — no bastion, no VPN, no static cluster credentials
  • Every request passes Cloudflare edge rules and Cloud Armor, which admits only Cloudflare IP ranges
  • Platform and database-level audit logging in place, with PHI deliberately kept out of log content
  • Continuous posture monitoring through Security Command Center catches configuration drift after launch
  • Recovery objectives defined, documented, and validated by an actual restore test
  • BAAs executed with both Google and Cloudflare, closing the vendor responsibility chain

More Work

View all

Facing a similar architectural challenge?

A 30-minute architecture review usually surfaces the quickest reliability and FinOps wins — no pitch, just a look at what you've got.

Ready for dispatch

Click to establish handshake link

Or find me here
Abdullah