Skip to main content

Keygrain

Deterministic password, SSH key, and wallet derivation from a master secret.

Install

pip install keygrain

CLI Usage

export KEYGRAIN_SECRET="your-master-secret"
keygrain me@example.com --site github.com
keygrain ssh me@example.com --name github
keygrain wallet me@example.com --name savings --chain bitcoin

Sync + Local Cache (read-only)

The CLI can download your synced services from the Keygrain server and store them in a local encrypted cache, then retrieve passwords / TOTP codes / SSH keys offline. The CLI is read-only: it never writes to the server. Add or change services with the browser extension or the Android app.

# Download and cache your account's services (the only networked command):
keygrain sync --email me@example.com

# List cached services (offline; no network):
keygrain list
keygrain list --type totp
keygrain list --site github.com

# Retrieve one credential (offline; no network):
keygrain get --site github.com               # password (default)
keygrain get --site github.com --totp         # current TOTP code
keygrain get --site github.com --ssh          # authorized_keys line
keygrain get --site github.com --ssh --private   # OpenSSH private key
keygrain get --id 550e8400-e29b-41d4-a716-446655440000   # select by exact id

# Seal a machine into offline-only mode (and lift it):
keygrain sync --lock
keygrain sync --unlock

# Self-hosted server:
keygrain sync --server https://sync.example.com

Site matching is a whole-label suffix match (github.com matches accounts.github.com but bank does not match fakebank.com). Any ambiguous match is a hard error listing the candidates — the CLI never guesses. The resolved (site, service-email) is always echoed to stderr before a secret is printed to stdout.

The cache lives at ~/.keygrain/accounts/<slug>.kg (AES-256-GCM, 0600). The master secret is never written to disk.

What a compromised sync server can (and cannot) do

The sync server only ever stores an encrypted blob plus a small unauthenticated metadata array (id + updated_at per service); it never sees your master secret or any derived credential. A hostile or compromised server therefore cannot exfiltrate secrets, decrypt your services, or leak data across accounts — the blob is AES-256-GCM encrypted under a key derived from your secret, and the CLI verifies its checksum and GCM tag before use.

The one thing a hostile server can influence is that unauthenticated metadata: by tampering with the id values it could, at most, cause get --id <uuid> to resolve to a different service that is still your own — it cannot inject a foreign or attacker-controlled entry. The mandatory stderr echo of the resolved (site, service-email) before any secret is printed is the guard: always read that line to confirm you got the credential you intended. (The CLI also drops any metadata id that is not UUID-shaped and strips control characters, so tampered ids cannot inject terminal escape sequences.)

Providing the master secret

sync, list, and get accept the master secret from exactly one of:

# Interactive hidden prompt (default when run in a terminal):
keygrain get --site github.com

# Environment variable — for CI/CD with injected secrets:
keygrain get --site github.com --secret-env KEYGRAIN_SECRET

# File — for Docker/Kubernetes secrets mounted as files:
keygrain get --site github.com --secret-file /run/secrets/keygrain_secret

A raw --secret VALUE argument is intentionally not provided (it would leak via ps / shell history). The CLI does not auto-load .env files.

Library Usage

from keygrain import derive_password, normalize_site

password = derive_password(
    secret=b"my-secret",
    email="me@example.com",
    site=normalize_site("github.com"),
)

Features

  • Argon2id key strengthening (64 MiB, 3 iterations)
  • HMAC-SHA256 derivation — single password compromise reveals nothing
  • TOTP seed derivation
  • SSH Ed25519 key derivation
  • BIP-39 wallet mnemonic derivation
  • BIP-85 child mnemonic derivation
  • Cross-platform compatible (Python, Kotlin, JavaScript)

Documentation

License

MIT

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

keygrain-1.0.1.tar.gz (67.0 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

keygrain-1.0.1-py3-none-any.whl (42.3 kB view details)

Uploaded Python 3

File details

Details for the file keygrain-1.0.1.tar.gz.

File metadata

  • Download URL: keygrain-1.0.1.tar.gz
  • Upload date:
  • Size: 67.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for keygrain-1.0.1.tar.gz
Algorithm Hash digest
SHA256 5f3f32e4a4a5c98eebad6a663b516f9260d11e8e86caeac95c4bd5e20651a42d
MD5 1b3646a205e3862a6ee768b508485d44
BLAKE2b-256 1a96481519848b0d08613ce157b5e3c5fc438b4113507efdf963331597bd2a6d

See more details on using hashes here.

Provenance

The following attestation bundles were made for keygrain-1.0.1.tar.gz:

Publisher: publish.yml on iheb-eddine/keygrain

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file keygrain-1.0.1-py3-none-any.whl.

File metadata

  • Download URL: keygrain-1.0.1-py3-none-any.whl
  • Upload date:
  • Size: 42.3 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for keygrain-1.0.1-py3-none-any.whl
Algorithm Hash digest
SHA256 1d93f72eaf72f1c628db951ef65765faff2ba69ba6a8f84e3bebe8b282fb8c99
MD5 829d308471a18e42d4f5522f1e8969ae
BLAKE2b-256 ebd35d51d1f5cbd087ddec1ca174e7f2176b3a608cb7aa327d28856621728f14

See more details on using hashes here.

Provenance

The following attestation bundles were made for keygrain-1.0.1-py3-none-any.whl:

Publisher: publish.yml on iheb-eddine/keygrain

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

This release

1.0.1 This release

2 files

1.0.0

2 files

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page