We start every codebase audit the same way: search the Git history for API keys, database passwords, and service credentials. We find them in roughly sixty percent of repositories we audit. Not in the current code -- most teams know to add .env to gitignore eventually -- but in the Git history. A developer committed a .env file in the first commit, removed it in the second, and assumed the problem was solved. It was not. Those credentials live in the history permanently.
Every team goes through the same progression. Level zero: hardcoded secrets in source code. Level one: .env files shared via Slack DMs. No access control, no audit trail, no rotation mechanism, no sync between environments, and trivially easy to accidentally commit or include in Docker images.
Level two: platform-managed secrets via Railway, Vercel, or Fly.io dashboards. A meaningful improvement -- secrets are encrypted at rest with platform-level access controls. The limitation: secrets siloed per platform, managed in three different places with three different interfaces.
Level three: centralized secrets management. A single source of truth for all secrets across all environments and platforms. We use Infisical for most projects -- open source, self-hostable, excellent TypeScript SDKs, integrates with every deployment platform we use. Doppler is the primary commercial alternative.
The workflow with centralized management: secrets stored in Infisical organized by project and environment. Developers authenticate via CLI and pull secrets into a local .env file that is gitignored and ephemeral. CI pipelines authenticate via service tokens and inject secrets at build time. Production containers pull secrets at startup via the SDK. Rotation means changing the value in one place -- all environments pick it up on next deploy.
The access control model matters. Junior developers access development secrets only. Tech leads and DevOps have production access. Secret access is logged for auditing. When a team member leaves, revoke their access and rotate any secrets they could see.
Two additional practices we enforce: every secret has a documented owner and rotation schedule (database passwords quarterly, API keys when team members change, JWT signing keys annually). And we use git-secrets as a pre-commit hook scanning staged files for patterns that look like credentials.
Setup time: two hours for new projects, half a day migrating existing ones. Not glamorous work. But a credential leak is the fastest path from "successful startup" to front page of Hacker News for the wrong reasons.
About the Author
Fordel Studios
AI-native app development for startups and growing teams. 14+ years of experience shipping production software.
The OWASP Top 10 reads like it was written for enterprises. We adapted it into actionable steps a two-person startup can implement in a week.
Your application has 1,200 dependencies. You vetted maybe ten of them. Supply chain attacks exploit the other 1,190. Here is how we protect our projects without abandoning npm entirely.
Your API has JWT authentication. Congratulations, you have solved ten percent of the security problem. Here are the other nine threats we find in almost every API audit.
We love talking shop. If this article resonated, let's connect.
Start a ConversationTell us about your project. We'll give you honest feedback on scope, timeline, and whether we're the right fit.
Start a Conversation