DEV Community

James
James

Posted on

I Built Authsia Because AI Agents Shouldn't Need to See Your Secrets

AI coding agents are becoming part of the normal developer workflow.

They run tests. They inspect repos. They start dev servers. They call CLIs. They debug deployment scripts. They sometimes need the same secrets a human developer needs: API keys, SSH keys, tokens, certificates, .env values.

And the default answer is still usually:

"Just paste the key into the terminal."

Or:

"Put it in .env and hope nothing weird happens."

That feels wrong.

Not because developers are careless, but because the tooling around local secrets was designed for a world where humans typed most commands themselves. Now we have terminals, scripts, CI jobs, local automation, and AI agents all touching the same workflows.

I built Authsia to make that boundary cleaner.

The Problem

Most developer secrets leak through boring places:

  • copying API keys into terminals
  • leaving plaintext values in .env
  • giving an AI agent access to an entire shell environment
  • loading SSH keys into a long-lived agent
  • pasting credentials into scripts during debugging
  • forgetting which tool used which secret and when

Traditional password managers are great for humans. They store credentials. They autofill websites. They help you generate strong passwords.

But developer workflows need something slightly different.

A developer secret often needs to be used by a command, not read by a person.

For example:

npm test
terraform plan
aws sts get-caller-identity
kubectl apply -f deploy.yaml
ssh ubuntu@server
Enter fullscreen mode Exit fullscreen mode

The question should not always be:

"How do I reveal this secret?"

It should be:

"How do I let this command use the secret without exposing more than necessary?"

That distinction matters even more when the command is launched by an AI agent.

What Authsia Is

Authsia is a local-first secret vault and CLI for macOS developer workflows.

It is built around terminals, workspaces, SSH, and local coding agents.

The core idea is simple:

Keep secrets in your local vault. Let tools request scoped access only when they need it.

Authsia gives you:

  • a macOS vault for passwords, notes, certificates, SSH keys, and OTP codes
  • a CLI for developer workflows
  • authsia:// secret references for commit-safe config
  • workspace-aware secret injection with masked command output
  • guarded terminal shims
  • Agent JIT approvals for scoped list and exec workflows
  • SSH signing through a local Authsia agent
  • local audit history

A Better .env Workflow

Instead of committing or copying plaintext secrets, Authsia can turn project secrets into references.

A repo can contain something like:

STRIPE_API_KEY=authsia://password/Stripe/password?folder=Project/API
DATABASE_URL=authsia://password/Database/password?folder=Project/API
Enter fullscreen mode Exit fullscreen mode

Those values are not secrets. They are references.

The real secret stays in Authsia.

Then, when you run a command:

authsia workspace run -- npm test
Enter fullscreen mode Exit fullscreen mode

Authsia resolves the references for the child process.

The secret does not need to live in your parent shell forever. It does not need to be pasted into chat. It does not need to sit raw in your repo.

For setup:

authsia workspace init
authsia workspace status
Enter fullscreen mode Exit fullscreen mode

The goal is not to make secret management fancy. The goal is to make the safer path feel like the normal path.

Concealed Secret Output

A secret can still leak even if you never paste it manually.

Sometimes a script prints the environment. Sometimes a test failure dumps config. Sometimes an agent runs the wrong diagnostic command.

That is why Authsia's exec path masks secret output.

When you run a command through Authsia:

authsia exec --env-file .env -- npm test
Enter fullscreen mode Exit fullscreen mode

or through a secret-bearing workspace command:

authsia workspace run -- npm test
Enter fullscreen mode Exit fullscreen mode

Authsia resolves the needed secrets for the child process, then masks approved secret values from stdout and stderr before they appear in the terminal.

So if a tool accidentally prints an injected API key, Authsia attempts to conceal the raw value in command output.

This is not a replacement for writing safe scripts. It does not make arbitrary programs harmless. But it gives the local workflow a useful last-mile guardrail: secrets can be used by the command without casually showing up in terminal output, agent logs, or copied debugging text.

Agent JIT Approvals

The biggest reason I built Authsia is simple:

AI agents should be able to use secrets without getting broad secret-reading powers.

That is where Agent JIT approvals come in.

JIT means just-in-time. In Authsia, JIT is triggered only when Authsia detects a local coding agent, IDE helper, or explicitly agent-marked command making an eligible Authsia request.

It is not triggered for normal human terminal usage. A developer typing Authsia commands directly keeps the normal session or biometric approval flow.

Agent JIT is intentionally narrow. It only permits:

  • list for approved metadata discovery
  • exec for running a command with scoped secrets injected into one child process

It does not permit plaintext export commands like:

  • get
  • read
  • load
  • inject

It also does not authorize OTP or SSH secret use through the JIT exec path. JIT exec is for password, certificate, and note references. SSH should use Authsia's SSH-agent flow instead.

An agent can discover approved metadata:

authsia list passwords --format table
Enter fullscreen mode Exit fullscreen mode

And it can run a command through Authsia:

authsia exec --env-file .env -- npm test
Enter fullscreen mode Exit fullscreen mode

In a workspace flow:

authsia workspace run -- npm test
Enter fullscreen mode Exit fullscreen mode

If that workspace command consumes authsia:// references, Authsia routes it through the same exec boundary where JIT approval can apply for detected agents. If there are no secret inputs, workspace run can pass through without firing JIT.

The grant is visible in Access Center, exact-folder scoped, tied to the agent/caller context, and temporary.

That is the boundary I want for AI-assisted development: agents can do useful work, but JIT does not become unlimited secret access.

Guarded Terminal

Sometimes you do not want to prefix every command with authsia workspace run.

For that, Authsia has a guarded terminal mode:

eval "$(authsia workspace guard --print-env)"
Enter fullscreen mode Exit fullscreen mode

Guarded mode adds Authsia shims for common developer tools like:

npm, pnpm, yarn, python, pip, docker, aws, kubectl, terraform, pulumi
Enter fullscreen mode Exit fullscreen mode

The idea is to keep familiar commands familiar, while still routing secret-bearing workflows through Authsia.

So instead of redesigning your whole workflow, Authsia sits at the boundary where secrets are needed.

SSH Is Part Of The Same Problem

SSH keys are developer secrets too.

Authsia includes a local SSH agent. After shell integration:

eval "$(authsia init zsh)"
Enter fullscreen mode Exit fullscreen mode

Git and SSH can use Authsia through SSH_AUTH_SOCK.

You can adopt existing keys:

authsia ssh adopt --path ~/.ssh --dry-run
authsia ssh adopt --path ~/.ssh --yes --folder Infra/SSH
Enter fullscreen mode Exit fullscreen mode

The aim is to move SSH usage away from loose private key files and toward a local approval and audit boundary.

It is still normal SSH. It is just less casual about where private keys live.

Local-First By Design

Authsia is intentionally local-first.

Secrets are stored in your local Keychain-backed vault, with optional iCloud Keychain sync depending on your setup. The CLI talks to the local app. The audit trail is local. There is no analytics layer trying to understand your workflow.

That matters to me because developer tools should not require sending sensitive workflow metadata to another service unless there is a very good reason.

For a lot of solo developers, indie hackers, and small teams, the local machine is still the center of gravity.

Authsia is built for that reality.

What Authsia Is Not

Authsia is not magic.

It does not make unsafe automation automatically safe. It does not replace good cloud IAM. It does not turn every local workflow into an enterprise access-control system.

What it does is give developers a better default for local secrets:

  • references instead of plaintext
  • child-process injection instead of parent-shell exposure
  • short-lived grants instead of permanent agent access
  • SSH agent integration instead of scattered private keys
  • auditability instead of guessing what happened

That is the layer I wanted as AI agents became part of my daily workflow.

Try Authsia

If you work with terminals, SSH, .env files, and AI coding agents, I would love for you to try Authsia and tell me where the workflow still feels rough.

Install with Homebrew:

brew install --cask james-liang-cs/authsia/authsia
Enter fullscreen mode Exit fullscreen mode

Then launch the app once and check the CLI:

authsia status
authsia workspace init
authsia workspace run -- npm test
Enter fullscreen mode Exit fullscreen mode

AI agents should be able to help us build software.

They should not need unlimited access to every secret in our shell to do it.

Top comments (0)