Your application gets the credential. Nobody else has to.

Warder separates using a secret from seeing one. Developers run the app, CI deploys it, agents test it: none of them are handed the value, and none of them need to be.

$ ward run -- npm run dev
What you can see
DATABASE_URL
••••••••••••••••••••••
STRIPE_SECRET_KEY
••••••••••••••••
AUTH_SECRET
••••••••••••••••••

Names, versions, expiry. Never the value, unless someone explicitly granted you that, and it is recorded when you use it.

What the process receives
DATABASE_URL
postgres://…@db.internal:5432/app
STRIPE_SECRET_KEY
sk_live_51H8xK2eZvKYlo2C…
AUTH_SECRET
8f3c9a1d4e7b2f6a0c5d8e3b…

Delivered into the environment block of the process you started. Not to your terminal, not to a file, not to your shell history.

The model

Two permissions, and no role grants either one

Most tools have a single “access” permission, so anyone who can deploy can also read. Warder splits it, and neither half comes with a job title.

Can use

The value reaches a process, and no human reads it.

What you grant your API server, your CI job, your test suite, an agent. It is the ordinary case, and it is the one that lets a credential do its job without becoming common knowledge.

Can see

A named person displays the plaintext, and it is recorded.

Sometimes genuinely necessary: pasting a key into a third-party console that has no other way in. It is a separate, deliberate grant, and every use of it has a name and a timestamp attached.

Owner, Admin, Developer, Viewer, those govern administration: creating projects, managing members, reading the audit log. None of them confers the ability to use or see a single secret value. That is always an explicit grant on a specific environment, which is what makes the answer to “who can read our production database password?” a short list instead of a guess.

In practice

What that actually changes

The same situations, with a different amount of work in them.

A contractor finishes and leaves.

Revoke their membership. Nothing rotates: they could use the database, they never held it.

An agent gets prompt-injected by a dependency README.

It holds USE_SECRET on development. It cannot print a value, reach production, rotate anything, or grant itself more.

Someone pushed a .env to a public repository.

There wasn’t one. The file holds two publishable keys and a project name.

You need to rotate a database password.

Rotate it in the dashboard and restart. No CI config, no manifests, no messages to the team.

Security asks who has read this credential.

One query against an append-only log. Usually the answer is nobody.

You revoke a token during an incident.

The next request is denied, including short-lived sessions already derived from it, rather than waiting for them to expire.

Integration

Three commands, and your code stays the same

Warder delivers values into the environment your process already reads. There is nothing to import and nothing to rewrite.

  1. 1

    Point the repository at an environment

    ward init --project payments-api --env development

    Writes .warder.json. Two names, no credentials: commit it.

  2. 2

    Sign in once per machine

    ward login

    Stores a session in your home directory. Developers set no environment variables at all.

  3. 3

    Run anything with the secrets injected

    ward run -- npm run dev

    Your code keeps reading process.env. No SDK, no imports, no code changes.

In production the same command runs, with the credential coming from your platform’s secret store instead of a login. Full walkthrough, including frontends and CI.

Limits

What Warder does not do

Stated here rather than buried, because a security tool that only advertises its wins is hard to evaluate.

  • It does not get you to zero credentials.

    Your application still holds one token that proves which application it is. Warder makes that one credential scoped, expiring and instantly revocable; it does not make it disappear. Nobody has solved that.

  • It does not stop an authorized process from reading its own environment.

    A process given DATABASE_URL can print it. The protection is that the grant was narrow and deliberate, not that the value is unreadable once delivered.

  • It does not protect values you ship to a browser.

    Anything in a client bundle is public no matter what produced it. Warder manages the server half and says so.

A credential should be available to the software that needs it, and to nobody else by default.