使用操作系统原生凭据存储的安全环境密钥管理。

myapp.dev、stripe-api.prod、work.staging)cmd 保存并重新运行命令(搜索、列出、运行、删除).env 文件(通过 audit 跟踪生成记录)eval $(envsec env)).env 文件加载密钥(带冲突检测)envsec tui),无需记忆命令即可管理密钥这是一个包含以下包的 monorepo:
| 包 | 描述 | npm |
|---|---|---|
envsec | 用于管理密钥的 CLI 工具 | |
@envsec/sdk | 用于以编程方式加载密钥的 Node.js / Bun SDK | |
@envsec/core | 核心引擎 — 操作系统凭据存储适配器 + 元数据数据库 | |
@envsec/tui | 用于密钥管理的交互式终端界面 |
如需从 Node.js 或 Bun 以编程方式访问密钥,请使用 @envsec/sdk:```bash
npm install @envsec/sdk
Please provide the Markdown content to translate.```typescript
import { loadSecrets } from "@envsec/sdk";
// Load and inject into process.env
await loadSecrets({ context: "myapp.dev", inject: true });
// Or use the client for full control
import { EnvsecClient } from "@envsec/sdk";
const client = await EnvsecClient.create({ context: "myapp.dev" });
const apiKey = await client.get("api.key");
await client.close();
请参阅完整的 SDK 文档,了解所有 API、多上下文支持及选项。
无需额外依赖。通过 security 命令行工具使用内置的钥匙串(Keychain)。
需要 libsecret-tools(提供 secret-tool 命令),该工具通过 D-Bus 与 GNOME Keyring、KDE Wallet 或任何 Secret Service API 提供程序通信。```bash
sudo apt install libsecret-tools
sudo dnf install libsecret
sudo pacman -S libsecret
需要运行中的 D-Bus 会话和密钥环守护进程(例如 `gnome-keyring-daemon`)。大多数桌面环境会自动处理这些。
### Windows
无需额外依赖。通过 `cmdkey` 和 PowerShell 使用内置的 Windows 凭据管理器。
## 安装
### Homebrew(macOS / Linux)```bash
brew tap davidnussio/homebrew-tap
brew install envsec
npm install -g envsec
### npx(无需安装)```bash
npx envsec
mise use -g npm:envsec
## 用法
大多数命令需要通过 `--context`(或 `-c`)指定上下文。
上下文是用于对机密进行分组的自由格式标签——例如 `myapp.dev`、`stripe-api.prod`、`work.staging`。
### 全局选项
以下选项适用于所有命令:
- `--context`、`-c` — 上下文名称(例如 `myapp.dev`、`stripe-api.prod`)。同时读取 `ENVSEC_CONTEXT` 环境变量
- `--debug`、`-d` — 启用调试日志
- `--json` — 以 JSON 格式输出,便于脚本处理
- `--db` — SQLite 数据库文件路径(默认:`~/.envsec/store.sqlite`)。同时读取 `ENVSEC_DB` 环境变量
### 自定义数据库路径
默认情况下,元数据存储在 `~/.envsec/store.sqlite`。你可以通过 `--db` 或 `ENVSEC_DB` 环境变量覆盖此路径:```bash
# Use a project-local database
envsec --db ./local-store.sqlite -c myapp.dev list
# Or via environment variable
export ENVSEC_DB=/shared/team/envsec.sqlite
envsec -c myapp.dev list
--db 标志优先于 ENVSEC_DB。使用场景包括项目专属数据库、网络驱动器上的团队共享数据库,以及使用临时存储的 CI/CD。
将密钥存储到操作系统凭据存储中。
<key> — 密钥名称(例如 api.key、db.password)--value、-v — 要存储的值(省略时显示交互式掩码提示)--expires、-e — 过期时长(例如 30m、2h、7d、4w、3mo、1y)```bashenvsec -c myapp.dev add api.key --value "sk-abc123"
envsec -c myapp.dev add api.key -v "sk-abc123"
envsec -c myapp.dev add api.key
envsec -c myapp.dev add api.key -v "sk-abc123" --expires 30d
envsec -c myapp.dev add api.key -v "sk-abc123" -e 6mo
### 获取机密
从操作系统凭据存储中检索机密值。
- `<key>` — 要检索的机密键名
- `--quiet`, `-q` — 仅打印原始值(不显示警告或额外输出)
- `--json` — 以 JSON 格式输出(包含 context、key、value、expires_at)```bash
envsec -c myapp.dev get api.key
# Print only the raw value (no warnings or extra output)
envsec -c myapp.dev get api.key --quiet
envsec -c myapp.dev get api.key -q
从操作系统凭据存储中移除一个机密。
<key> — 要删除的机密键名(如果使用 --all 则可选)--yes, -y — 跳过确认提示--all — 删除上下文中的所有机密```bash
envsec -c myapp.dev delete api.keyenvsec -c myapp.dev del api.key
### 重命名密钥
在同一上下文中重命名密钥。值和过期元数据将被保留。
- `<old-key>` — 当前密钥名称
- `<new-key>` — 新密钥名称
- `--force`, `-f` — 如果目标已存在则覆盖```bash
# Rename a key
envsec -c myapp.dev rename old.key new.key
# Overwrite target if it already exists
envsec -c myapp.dev rename old.key existing.key --force
列出上下文中的所有密钥键及其元数据。
--json — 以 JSON 格式输出```bash
envsec -c myapp.dev list### 列出所有上下文
列出所有可用的上下文及其密钥数量。
- `--json` — 以 JSON 格式输出```bash
# Without --context, lists all available contexts with secret counts
envsec list
使用 glob 模式搜索机密或上下文。
<pattern> — 用于搜索的 Glob 模式(例如 api.*、myapp.*)--json — 以 JSON 格式输出```bashenvsec -c myapp.dev search "api.*"
envsec search "myapp.*"
### 在上下文之间移动密钥
将密钥从一个上下文移动到另一个上下文。移动后,源密钥将被删除。
- `<pattern>` — 用于移动的 Glob 模式或精确密钥(使用 `--all` 时可省略)
- `--to`, `-t` — 将密钥移动到的目标上下文
- `--all` — 移动源上下文中的所有密钥
- `--force`, `-f` — 覆盖目标上下文中已有的密钥
- `--yes`, `-y` — 跳过确认提示```bash
# Move a single secret
envsec -c myapp.dev move api.token --to myapp.prod
# Move secrets matching a glob pattern
envsec -c myapp.dev move "redis.*" --to myapp.prod -y
# Move all secrets from one context to another
envsec -c myapp.dev move --all --to myapp.prod -y
# Overwrite existing secrets in the target context
envsec -c myapp.dev move "redis.*" --to myapp.prod --force -y
将机密从一个上下文复制到另一个上下文。源机密保持不变。
<pattern> — 用于复制的 Glob 模式或精确键(如果使用 --all 则可选)--to, -t — 要将机密复制到的目标上下文--all — 从源上下文复制所有机密--force, -f — 覆盖目标上下文中已有的机密--yes, -y — 跳过确认提示```bashenvsec -c myapp.dev copy api.token --to myapp.staging
envsec -c myapp.dev copy "redis.*" --to myapp.staging -y
envsec -c myapp.dev copy --all --to myapp.staging -y
envsec -c myapp.dev copy "redis.*" --to myapp.staging --force -y
### 使用机密运行命令
通过占位符插值机密值,或将其作为环境变量注入来执行命令。
- `<command>` — 要执行的命令。使用 `{key}` 占位符进行机密插值
- `--inject`, `-i` — 将所有上下文机密作为环境变量注入(`KEY.NAME` → `KEY_NAME`)
- `--save`, `-s` — 保存此命令以供后续使用
- `--name`, `-n` — 已保存命令的名称(与 `--save` 一起使用时,若省略则交互式提示)```bash
# Placeholders {key} are resolved with secret values before execution
envsec -c myapp.dev run 'curl {api.url} -H "Authorization: Bearer {api.token}"'
# Any {dotted.key} in the command string is replaced with its value
envsec -c myapp.prod run 'psql {db.connection_string}'
# Inject ALL context secrets as environment variables (KEY.NAME → KEY_NAME)
envsec -c myapp.dev run --inject 'node server.js'
envsec -c myapp.dev run -i 'docker compose up'
# Combine --inject with placeholders
envsec -c myapp.dev run --inject 'curl {api.url} -H "Authorization: Bearer $API_TOKEN"'
# Save the command for later use with --save (-s) and --name (-n)
envsec -c myapp.dev run --save --name deploy 'kubectl apply -f - <<< {k8s.manifest}'