How Infisical moves secrets from a hardcoded problem to a managed one. The platform components, auth flows for machines and humans, the project-environment-path hierarchy, SDK delivery patterns, and where self-hosting changes the trust model.
Every application has secrets. Database URLs, API keys, signing tokens, OAuth client IDs. The naive solution is a .env file. It works for one developer on one project. It breaks when you have three environments, four services, a CI system, and a Kubernetes cluster that all need different values for the same key.
Infisical is an open source platform that treats secrets as a first-class resource. Instead of copying values into environment files or injecting them through a patchwork of CI settings and K8s secrets, you store them once and deliver them through a controlled interface. The platform knows which application is asking, which environment it runs in, and what paths it has permission to read. Everything else is denied by default.
The platform ships five integrated products: Secrets Management, Secrets Scanning, Certificate Management (PKI), a KMS for data encryption, and Privileged Access Management. Most teams start with secrets management and expand from there.
All secrets in one place. Project, environment, and folder-path scoped. Fine-grained RBAC determines who and what can read each path.
Service accounts for machines. Auth via Universal Auth (clientId/clientSecret), OIDC, AWS, GCP, Azure, Kubernetes, or SPIFFE. Returns short-lived tokens.
Generate short-lived credentials on demand. Database users that expire after 15 minutes. No long-lived static passwords for high-value systems.
Detect hardcoded credentials in git history, CI pipelines, and PR diffs before they reach production. Integrates with GitHub, GitLab, and Bitbucket.
Infisical is a delivery infrastructure, not just a key-value store. A secret lives in the platform under a project, environment, and folder path. Applications get their secrets through one of four delivery paths: CLI injection, SDK runtime fetch, Kubernetes operator sync, or Agent daemon. The delivery path determines when the secret leaves the vault and how long it lives in the process. Understanding these paths is the foundation for choosing the right integration pattern.
Infisical is built from four infrastructure pieces. The API backend serves all requests. PostgreSQL stores all secrets and platform data. Redis handles caching, async queues, and cron jobs. The clients are how users and machines interact with the API.
The REST API is the single entry point for everything. A request arrives, the API validates the bearer token, checks RBAC for the requested operation and path, then either returns the secret value or denies the request. There is no side channel. The audit log entry is written on every request, success or failure.
Infisical Cloud routes all traffic through Cloudflare, which enforces TLS and terminates DDoS traffic. Self-hosted instances must configure TLS at the reverse proxy layer. The API requires TLS 1.2 or higher and does not serve requests over plaintext HTTP.
All secrets, user records, project configs, RBAC policies, and audit events live in Postgres. Secret values are encrypted at the application layer before being written. The database holds ciphertext, not plaintext. An attacker with read access to the Postgres instance sees encrypted blobs without the decryption keys, which live separately in the API server's key store.
For Infisical Cloud, the database is a managed Postgres instance inside the platform's private network. For self-hosting, you provide the Postgres connection string.
Redis serves three roles. It caches frequently-accessed resources (project metadata, RBAC policies) so that common read paths do not hit Postgres on every request. It backs the async task queue for long-running operations like secret rotation jobs and webhook delivery. It also stores scheduled cron job state, including rotation schedules for dynamic secrets.
The caching layer is a correctness concern, not just a performance one. An RBAC policy change must invalidate cached policies. Infisical handles this internally; you should not bypass the API to write directly to the database, because the cache invalidation will not fire.
Six delivery surfaces exist for applications and users:
infisical): Terminal tool for interactive use, scripting, and CI pipelines. infisical run -- <command> spawns a child process with secrets injected as environment variables. Nothing is written to disk.process.env, or query individual values by name.Infisical organizes everything under four levels: organization, project, environment, and folder path. Every secret lives at exactly one leaf in this tree. The tree is how RBAC scopes access.
A project is the top-level container for one service or product. Each project has its own set of environments, its own secret namespace, and its own access control list. Machine Identities are assigned to projects and scoped to specific environment+path combinations within them.
Each project gets three environments by default: dev, staging, and production. You can add custom environments. The same secret name can exist in each environment with a different value. A DATABASE_URL in dev points to a local Postgres; the same key in production points to the managed instance with SSL and a connection pooler.
Within an environment, secrets are organized into folder paths. The root path / holds shared top-level secrets. Subpaths group by domain: /ai, /database, /payments, /storage. This matters for RBAC. A Machine Identity running the billing service can be scoped to production /payments only. It cannot read the AI keys in production /ai even if it tries. The scoping is enforced at the API layer, not at the application layer.
Infisical uses path-based RBAC rather than per-secret permissions. This means you design your folder structure with access control in mind, not as an afterthought. A payment service CI identity scoped to production /payments automatically gets access to every secret under that path. Adding a new secret to that path requires no RBAC change. Moving a secret to a different path may require updating role assignments. Design paths around the teams and services that need them, not around alphabetical ordering.
A Machine Identity is an entity that represents a workload. Think of it as the Infisical equivalent of an AWS IAM role or a GCP service account. You create one identity per environment per service. Each identity gets a role assignment and an authentication method. At runtime the workload authenticates using that method and receives a short-lived access token. All subsequent API calls use that token.
Create a Machine Identity in the dashboard. Assign a role (viewer, operator, custom). Configure an auth method and token TTL.
The workload presents credentials to the Infisical API using the configured method (clientId/secret, OIDC JWT, AWS SigV4, etc.).
Infisical validates the credentials and returns a short-lived access token. The TTL is configured per identity (default: 7 days for Universal Auth; shorter for OIDC).
All subsequent API requests use the access token as a bearer token. The API enforces the identity's RBAC scope on every request.
The default auth method for servers and CI pipelines. The identity gets a clientId and a clientSecret. These two values are the bootstrap credentials: the only secrets that must exist outside Infisical. Store them in your platform's secret management (Vercel env vars, GitHub Actions secrets). At startup, the application exchanges them for a short-lived Infisical access token and uses that token for all secret fetches.
For workloads running on platforms that issue OIDC tokens (GitHub Actions, GitLab CI, AWS EKS, GCP Cloud Run), you can skip the clientSecret entirely. The CI system issues a JWT bound to the workflow run. Infisical verifies the JWT signature against the provider's JWKS endpoint, checks audience and claim conditions you configure, and issues an access token. No static secret is exchanged. The bootstrap problem disappears.
This is the preferred method for GitHub Actions. The workflow requests an OIDC token, Infisical verifies it, and secrets are fetched for that run only. A leaked token is useless after the run ends.
For workloads on major cloud platforms, Infisical can verify platform-issued identity assertions directly. An EC2 instance authenticates using AWS SigV4 against the EC2 metadata service. A GKE pod presents its service account JWT. An AKS deployment uses its managed identity. The platform validates the assertion against its native authentication endpoint and issues an Infisical token. No client secret is managed by the application at all.
Universal Auth login endpoints have lockout enabled by default. 3 consecutive failed login attempts within a 30-second window locks the endpoint for 5 minutes. This is a brute-force defense for the bootstrap credentials. OIDC and platform-native methods are not affected because they do not use passwords. For Universal Auth in automated systems, use a retry budget with backoff rather than aggressive retry loops, since failures will lock the identity.
| Auth Method | Bootstrap Secret Required | Best For | Token Lifetime |
|---|---|---|---|
| Universal Auth | clientId + clientSecret | Any server, Vercel, Render, VMs | Configurable (1h to 7d) |
| OIDC Auth | None (JWT from provider) | GitHub Actions, GitLab CI, GKE, EKS | Per job/run |
| AWS Auth | None (EC2/Lambda metadata) | EC2, Lambda, ECS, EKS | Configurable |
| Kubernetes Auth | None (pod service account JWT) | Any K8s cluster with OIDC | Configurable |
| Token Auth | Static token (rotate manually) | Simple scripts, legacy integrations | Until revoked |
| SPIFFE Auth | None (SVID from SPIRE) | Service mesh workloads with SPIRE | Per SVID rotation |
Once authenticated, the application needs to get secrets into its process. The right method depends on when you need the secret, whether the runtime restarts frequently, and how the rest of your stack is built.
infisical runThe simplest integration. Wrap your start command with infisical run --env=production -- node server.js. Infisical authenticates, fetches all secrets at the configured path, and injects them as environment variables into the child process. The parent shell sees nothing. Nothing is written to disk. The secrets are visible only inside the running process.
The SDK authenticates at process startup and fetches secrets at runtime. This is the right choice for long-running servers, Vercel functions, and any runtime where you want to handle secret values in code rather than rely on environment variable injection. The key pattern: authenticate once at module scope, cache the SDK client, then fetch secrets by name or inject a whole path into process.env in one call.
Note that getSecret throws a StatusCode=404 error when the secret is absent. This is correct behavior. A missing secret at startup should crash the process loudly, not produce a silent undefined that causes a downstream failure two minutes later.
The Kubernetes Operator syncs Infisical secrets into Kubernetes Secret objects using CRDs. Applications read from K8s secrets as normal through environment variable references or volume mounts. The operator watches for changes in Infisical and re-syncs on updates. This keeps the interface familiar for teams already using K8s secrets, while making Infisical the single source of truth for values.
The operator authenticates using Kubernetes Auth (the pod's own service account JWT). No static credentials are stored in the cluster. The CRD definition specifies which project, environment, and path to sync, and into which Kubernetes namespace and Secret name to write.
The Agent is a sidecar daemon that handles token lifecycle and secret templating for processes that cannot use the SDK or CLI. It authenticates, keeps its token refreshed, and can write rendered configuration files using a template syntax. Applications read a local file or socket rather than calling the Infisical API directly. The Agent abstracts the auth complexity away from the application entirely.
For platforms that expect secrets in their own native format, Infisical can push values outward. Supported targets include GitHub Actions repository secrets, Vercel project environment variables, AWS Parameter Store, AWS Secrets Manager, GCP Secret Manager, and more. The sync runs when secrets change in Infisical. This means you edit secrets once in Infisical and let the sync push to the downstream platform, rather than maintaining values in two places.
Use CLI injection for local development and CI scripts. Use the SDK for servers that start infrequently and need to handle secret values programmatically. Use the Kubernetes Operator when your team already manages K8s secrets and you want to minimize application changes. Use the Agent for legacy applications that read config files and cannot be changed to use an SDK. Use Secret Syncs only for platforms where you cannot run any Infisical client directly (e.g., Netlify build environment, third-party SaaS that reads from GitHub secrets).
Infisical's security model covers encryption at rest and in transit, authenticated and authorized access for every request, and a full audit trail of every operation. The threat model is explicit about what it covers and what it does not.
Secret values are encrypted at the application layer before being written to PostgreSQL. The database holds ciphertext. Infisical uses proven symmetric encryption (AES-256) for stored secrets. The encryption keys are managed by the API server, not stored alongside the ciphertext in the database.
This design means that read access to the PostgreSQL instance does not expose secret values. An attacker who dumps the database gets encrypted blobs. They need the application-layer keys to decrypt them, and those keys are not in the database.
All client-to-server communication goes over TLS. Infisical Cloud routes through Cloudflare, which enforces TLS 1.2 as a minimum and provides DDoS protection. For self-hosted instances, TLS termination is the operator's responsibility (typically at an nginx or Caddy reverse proxy in front of the Infisical containers).
Every operation generates an audit event. Reads, writes, role changes, auth failures, and policy updates all appear in the audit log with a timestamp, actor identity, source IP, user agent, and relevant metadata. The log is append-only. You cannot delete entries through the API. For compliance requirements (SOC 2, ISO 27001), the audit log is the primary evidence trail for secret access patterns.
These are not defects. They define what the system is designed to defend against and where operational controls must compensate.
| Security Property | Mechanism | Where It Applies |
|---|---|---|
| Secrets encrypted at rest | AES-256, application-layer | PostgreSQL storage |
| Secrets encrypted in transit | TLS 1.2+ (Cloudflare on Cloud) | Client to API, API to storage |
| Authenticated access | Bearer token on every request | All API endpoints |
| Authorized access | RBAC scoped to project/env/path | Every read, write, and admin op |
| Audit trail | Append-only event log | All mutations and sensitive reads |
| Short-lived tokens | TTL on all machine access tokens | Machine Identities |
| Brute-force protection | Lockout after 3 failures in 30s | Universal Auth login endpoint |
| IP restrictions on tokens | Configurable per Machine Identity | Machine Identity access tokens |
Infisical is fully open source under MIT license. The same codebase powers both Infisical Cloud and self-hosted instances. The choice between them is a data residency and operational question, not a features question.
Managed service at app.infisical.com. Infisical operates PostgreSQL, Redis, and the API layer. All traffic routes through Cloudflare. The team handles upgrades, backups, uptime, and security patches. SOC 2 Type II certified. For most teams, this is the right default: it removes operational overhead and provides enterprise compliance out of the box.
Pricing is per-seat for human users. Machine Identities and API calls are not per-seat. The free tier supports unlimited secrets and environments with 5 member seats and 5 machine identities. Paid tiers start at $6 per seat per month and unlock SCIM provisioning, SAML SSO, and advanced RBAC.
Run Infisical on your own infrastructure. The official deployment path is Docker Compose or Helm chart. You bring PostgreSQL and Redis. The API containers connect to your storage. Your reverse proxy handles TLS. Infisical provides the application containers; you provide the substrate.
Self-hosting is worth the operational cost in specific cases: data residency requirements under regulations like GDPR or KDPA 2019 that restrict cross-border data transfer, air-gapped environments where outbound internet is not permitted, or organizations that cannot allow any third party to hold encrypted copies of their secrets even in ciphertext form.
When self-hosting, the siteUrl parameter on the SDK and the --domain flag on the CLI must point to your instance URL. The default https://app.infisical.com will not work. This is a common misconfiguration during initial setup.
A third pattern: run the Infisical API yourself but back it with a managed database (Neon, Supabase, AWS RDS). This keeps compute and application data on your infrastructure while offloading database operations to a managed service. The Infisical API does not care where PostgreSQL lives as long as it gets a valid connection string.
| Dimension | Cloud | Self-Hosted |
|---|---|---|
| Data residency | US/EU regions; your secrets transit Infisical infra | Full control; secrets never leave your network |
| Ops burden | Zero; Infisical manages all infra | You run Postgres, Redis, containers, TLS, upgrades |
| Compliance certifications | SOC 2 Type II, ISO 27001 (Cloud) | Must achieve your own certification for your instance |
| Feature parity | Full; latest features land on Cloud first | Depends on the version you run; manual upgrade path |
| Uptime SLA | 99.99% on Enterprise tier | Your responsibility; no SLA from Infisical |
| Air-gap support | Not possible; requires outbound internet | Supported; no outbound dependencies after setup |
Infisical Cloud pricing is seat-based, not usage-based. You pay per human member, not per secret fetch or API call. Machine Identities are not charged per-seat. This means a team with 4 developers and 30 microservices, each with its own Machine Identity, pays for 4 seats. The 30 service identities making thousands of secret fetches per day add nothing to the bill.
The free tier gives you unlimited secrets, environments, and folders, with 5 member seats and 5 Machine Identities. The 5-identity limit is the constraint that forces most teams off free. Each microservice, CI pipeline, and staging environment typically needs its own identity for least-privilege scoping.
Self-hosting costs shift from licensing to infrastructure and engineering time. Running Postgres, Redis, and the Infisical containers on a cloud VM costs roughly $30 to $80 per month for a small deployment. Add managed database and Redis (e.g., Neon + Upstash) and it lands around $20 to $50. The hidden cost is the engineering time to handle upgrades, backups, and incident response when the secrets platform itself is unavailable.
| Scenario | Cloud Cost | Notes |
|---|---|---|
| Startup: 3 devs, 5 services | $0 (free tier) | 5 seats, 5 identities covers this exactly |
| Small team: 8 devs, 20 services | $48/mo (Pro, $6/seat x 8) | 20 Machine Identities on Pro tier (unlimited) |
| Mid-size: 25 devs, 60 services | $150/mo (Pro, $6/seat x 25) | Still seat-based; service count is irrelevant |
| Self-hosted on VPS | $30 to $80/mo infra | Plus ops time for upgrades and incident response |
| Self-hosted with managed DB | $20 to $50/mo | Neon + Upstash Redis + 1x small VM for API |
Universal Auth requires two bootstrap values: INFISICAL_CLIENT_ID and INFISICAL_CLIENT_SECRET. These must live somewhere before Infisical can fetch anything. Common patterns: store them in Vercel project environment variables (for Vercel-hosted services), in GitHub Actions secrets (for CI), or in the platform's native secret system (AWS Secrets Manager, GCP Secret Manager, Azure Key Vault). The bootstrap secret is narrowly scoped: it only grants access to the paths that specific Machine Identity is assigned to. A leaked bootstrap secret for the payments service cannot access the AI keys or any other identity's paths.
production /payments or staging /database limits blast radius when a credential is compromised.clientSecret to rotate, leak, or forget to revoke.InfisicalSDK instance at module scope, authenticate once, and reuse it across all requests in that process lifetime.getSecret throws on missing keys by design. A missing secret at startup should crash the process. Catching the error and returning undefined turns a deployment configuration mistake into a runtime failure that is much harder to diagnose./ai should contain everything the AI service needs and nothing the payments service needs. Path-based RBAC means your folder structure is your access control policy. Refactoring paths later requires updating role assignments.infisical scan belongs in CI, not just local development. Running the scanner only locally misses credentials that get committed in branches and PRs before the scan runs. Add it as a required CI step so that hardcoded secrets block the merge rather than reaching production.New deep-dives on systems architecture, delivered when they ship.