---
title: "Security & secrets"
description: "SOPS secrets, the age key, Filen and Anytype credentials, and path-guard hardening."
---

# Security & secrets

This configuration enforces strict security measures.

- **Secrets Management**: Secrets are SOPS-encrypted and stored under `secrets/`.
  Access to sensitive directories (e.g. `~/.ssh`, `~/.gnupg`) is restricted.
- **Path Guard**: the `path-guard.ts` extension enforces a path allowlist/denylist for file-access tools (`read`, `write`, `edit`) and `bash` commands.
- **Model Routing**: providers and models are configured in `pi-models.json` (see [models.mdx](models.mdx)).
- **Cost Tracking**: extensions track token usage and cost across providers (see [extensions.mdx](extensions.mdx)).
- **Hardening**: `modules/hardening.nix` installs `vulnix` and `trivy`, sets a restrictive `UMASK`, and tightens shell-history permissions.
  It also defines `sec-scan`, `trivy-scan`, and `sec-update` shell aliases.

## Secrets

Secrets are stored as SOPS-encrypted YAML files under `secrets/` and decrypted at activation time by `sops-nix`.

To edit a secret you need your age private key.
SOPS searches several locations via env vars; on this machine the key lives at `~/.config/sops/age/keys.txt`:

```sh
SOPS_AGE_KEY_FILE=~/.config/sops/age/keys.txt sops secrets/filen.yaml
# to encrypt secrets and add metadata, and replace file
SOPS_AGE_KEY_FILE="$HOME/.config/sops/age/keys.txt" sops --encrypt --in-place secrets/anytype.yaml
```

SOPS decrypts the file, opens it in `$EDITOR`, and re-encrypts on save.
After editing, re-run `home-manager switch` so activation scripts pick up the new values.

### Filen credentials

`secrets/filen.yaml` holds the `email` and `password` keys used to authenticate `filen-cli`.
`modules/shell.nix` exports them as `FILEN_CLI_EMAIL` and `FILEN_CLI_PASSWORD` at shell startup (the Rust `filen-cli` reads these env vars).
The old Node CLI's `~/.filen-cli/.filen-cli-credentials` file is no longer used.

### Anytype credentials

`secrets/anytype.yaml` holds the `apiKey` and `workspaceId` keys used by the Anytype integration.
They are declared in `modules/ai.nix` and exported as `ANYTYPE_API_KEY` and `ANYTYPE_WORKSPACE` by `modules/shell.nix` for use by the pi extension.
See the [Anytype integration](extensions.mdx#anytype-integration).

## The path-guard extension

`pi-extensions/path-guard/` enforces a read/write allowlist and denylist for agent tool calls.
It blocks environment dumps and secret-named variable reads, and redacts leaked secret values from tool output.
In a Firstmate session (the `~/firstmate` home or a worker it launches) the outside-cwd confirmation for reads and `bash` under `$HOME` is skipped; the denylist still applies.

## Other security-adjacent extensions

- `pi-extensions/curl/` restricts HTTP requests to a configured allowlist of domains and paths (see [extensions.mdx](extensions.mdx)).
- `pi-extensions/credential-leak/` scans session transcripts for leaked credentials and redacts leaked secret values.
- `pi-extensions/azure-guard/` blocks Azure/Microsoft 365 tools in unattended Firstmate sessions (see [extensions.mdx](extensions.mdx)).
