# SecretSpec > SecretSpec is a declarative secrets manager for development workflows. It separates secret **declaration** from secret **storage**: commit a `secretspec.toml` that declares what secrets your application needs, while the actual values live in a secure provider (system keyring, 1Password, Vault, etc.). SecretSpec answers three questions for every project: - **WHAT** secrets does the application need? - **HOW** do requirements change per environment (via profiles)? - **WHERE** are the actual values stored (via providers)? ## Quick Start 1. Initialize: `secretspec init --from .env` or create `secretspec.toml` manually 2. Set secrets: `secretspec set DATABASE_URL` 3. Check status: `secretspec check` 4. Run commands with secrets: `secretspec run -- npm start` ## Configuration Example ```toml [project] name = "my-app" revision = "1.0" [profiles.default] DATABASE_URL = { description = "PostgreSQL connection string", required = true } REDIS_URL = { description = "Redis cache" } TLS_CERT = { description = "TLS cert", as_path = true } DB_PASSWORD = { description = "DB password", type = "password", generate = true } [profiles.development] DATABASE_URL = { default = "postgresql://localhost/dev" } ``` ## Composed Secrets (0.16+) `composed` derives a read-only value from other declared secrets with strict, order-independent `${UPPERCASE_NAME}` references. Names must match `[A-Z][A-Z0-9_]*`; it does not perform dotenv, shell, ambient-environment, or recursive expansion. ## Type-safe Rust SDK ```rust secretspec_derive::declare_secrets!("secretspec.toml"); fn main() -> Result<(), Box> { let resolved = SecretSpec::builder() .with_provider("keyring://") .with_profile("development") .with_reason("start application") .load()?; println!("Database: {}", resolved.secrets.database_url); if let Some(redis_url) = &resolved.secrets.redis_url { println!("Redis: {redis_url}"); } resolved.secrets.set_as_env_vars(); println!("Profile: {}", resolved.profile); println!("Provider: {}", resolved.provider); Ok(()) } ``` ## Migration Move every secret between providers without changing application code: ```bash $ secretspec import dotenv://.env.production ``` ## Providers Values can be resolved from: keyring (default), KeePass KDBX (0.17+), dotenv files, plaintext file directories (0.19+), environment variables, systemd service credentials (0.17+), 1Password, Gopass (0.15+), LastPass, Dashlane (0.18+, read-only), Pass, Proton Pass, Passbolt (0.19+), Keeper Secrets Manager (0.18+), Google Cloud Secret Manager, AWS Secrets Manager, AWS Systems Manager Parameter Store (0.18+), Scaleway Secret Manager (0.17+), HashiCorp Vault, OpenBao (0.17+), Bitwarden Password Manager (0.18+), Bitwarden Secrets Manager, Azure Key Vault, Azure App Configuration (0.20+), Infisical (0.16+), age (0.17+), or SOPS (0.17+). Fly.io application secrets can be published through the write-only fly provider (0.20+). The null provider (0.19+) uses manifest defaults, ephemeral generation, or ephemeral run prompts without storage. ## Documentation Sets - [Abridged documentation](https://secretspec.dev/llms-small.txt): a compact version of the documentation for SecretSpec, with non-essential content removed - [Complete documentation](https://secretspec.dev/llms-full.txt): the full documentation for SecretSpec ## Notes - The complete documentation includes all content from the official documentation - The content is automatically generated from the same source as the official documentation