关于 detecting-secrets
detecting-secrets 是用于代码审查的安全技能,帮助审查者查找硬编码凭据并区分真实秘密与测试值、占位符或加密内容。它还提供暴露凭据后的轮换、代码清理和防止复发的处理步骤。
主要功能
- 01识别密钥、口令和连接字符串
- 02检查常见配置与代码藏匿位置
- 03结合上下文排除误报
- 04提供凭据轮换与代码清理步骤
- 05指导检查 GitHub 告警和提交历史
适用场景
- 01审查代码中的硬编码凭据
- 02核实测试数据或占位符是否为误报
- 03发现凭据泄露后规划轮换与清理
- 04检查 GitHub Secret Scanning 告警
安装
复制下面的命令,在终端中运行。
$
npx skills add https:/ / github.com/ bitwarden/ ai-plugins --skill detecting-secrets安装后在 Claude Code 中输入/detecting-secrets确认已加载。
详细介绍
密钥模式
在代码中查找以下类别的硬编码密钥:
高置信度模式
| 类型 | 模式示例 |
|---|---|
| API 密钥 | AKIA[0-9A-Z]{16}(AWS)、AIza[0-9A-Za-z_-]{35}(Google)、赋给名称为 *apiKey*、*api_key* 的变量的字符串 |
| 连接字符串 | Server=...;Password=...、mongodb://user:pass@host、postgres://user:pass@host |
| 私钥 | -----BEGIN RSA PRIVATE KEY-----、-----BEGIN OPENSSH PRIVATE KEY----- |
| 令牌 | ghp_[A-Za-z0-9]{36}(GitHub PAT)、xoxb-(Slack 机器人)、sk-(OpenAI) |
| 密码 | 赋给名称为 *password*、*passwd*、*secret*、*credential* 的变量的值 |
| 证书 | 含有内嵌密码的 PFX/P12 文件、含有私钥的 PEM 文件 |
低置信度模式(需要结合上下文判断)
- 配置中的 Base64 编码字符串(可能已加密,也可能是明文密钥)
- JWT 令牌(可能是测试令牌,也可能是生产令牌)
- 长度为 32 个或更多字符的十六进制字符串(可能是加密密钥,也可能是哈希值)
- 内嵌凭据的 URL(
https://user:pass@host)
上下文感知检测
区分真实密钥与误报。并非每个匹配的模式都表示实际密钥——请结合上下文判断:
测试固定数据和模拟数据
// NOT a real secret — test fixture with obvious fake value
var testApiKey = "test-api-key-not-real-12345";
var mockPassword = "P@ssword123"; // Used only in unit tests
// REAL secret — production-looking value in non-test code
var apiKey = "sk-proj-abc123def456ghi789jkl012mno345pqr678stu901vwx";
判断标准:
- 它是否位于测试目录中(
**/test/**、**/tests/**、**/*.Test/**)? - 值中是否包含明显的占位文本(“test”“fake”“mock”“example”“placeholder”)?
- 该值是否用于断言或模拟设置?
示例值和占位值
// NOT a real secret — documented example
{
"apiKey": "YOUR_API_KEY_HERE"
}
// REAL secret — actual value in config
{
"apiKey": "sk-proj-abc123def456ghi789jkl012mno345pqr678stu901vwx"
}
加密或哈希值
- 哈希密码(bcrypt
$2b$、argon2$argon2id$)不是密钥——它们已得到妥善存储 - 采用适当密钥管理的加密值,从同样的意义上说不是密钥
- 但如果加密密钥本身被硬编码,它就是密钥
常见隐藏位置
审核密钥时,请搜索以下位置:
| 位置 | 查找内容 |
|---|---|
appsettings.json / appsettings.Development.json | 连接字符串、API 密钥、服务凭据 |
.env / .env.local | 包含真实值的环境变量定义 |
web.config / app.config | 机器密钥、连接字符串 |
docker-compose.yml / Dockerfile | 含有凭据的 ENV 指令、包含密钥的构建参数 |
CI/CD 文件(.github/workflows/*.yml) | 内联密钥,而不是 ${{ secrets.* }} 引用 |
| 测试数据填充脚本 / 迁移文件 | 数据库密码、服务帐户凭据 |
| 注释和 TODO 备注 | 留在注释中的“临时”凭据 |
| 默认参数值 | function connect(password = "admin123") |
| 常量文件 | 集中定义的凭据 |
GitHub 密钥扫描集成
# List all secret scanning alerts
gh api /repos/{owner}/{repo}/secret-scanning/alerts --jq '.[] | {number, state, secret_type, secret_type_display_name, created_at, push_protection_bypassed}'
# Get details for a specific alert
gh api /repos/{owner}/{repo}/secret-scanning/alerts/{alert_number}
# List alerts that bypassed push protection
gh api "/repos/{owner}/{repo}/secret-scanning/alerts?state=open" --jq '.[] | select(.push_protection_bypassed == true)'
推送保护可阻止包含检测到的密钥的提交被推送。有人绕过推送保护时,系统会标记警报——请格外仔细地审查这些警报。
补救工作流
在代码中发现机密时,请按以下顺序处理:
1. 立即轮换
假设任何已提交的机密都已泄露。即使仓库是私有的,机密也可能已被缓存、记录到日志,或被 CI/CD 系统访问。
- 撤销现有凭据
- 生成新凭据
- 在所有使用该凭据的地方(服务、部署)更新它
2. 从代码中移除
将硬编码的机密替换为安全引用:
// WRONG — hardcoded secret
var connectionString = "Server=prod.db;Password=s3cr3t!";
// CORRECT — environment variable
var connectionString = Environment.GetEnvironmentVariable("DB_CONNECTION_STRING");
// CORRECT — Azure Key Vault (Bitwarden's approach)
var connectionString = await keyVaultClient.GetSecretAsync("db-connection-string");
3. 从 Git 历史记录中移除(如有需要)
如果机密已提交到公开仓库,或即将公开的仓库:
# Using git filter-repo (preferred over filter-branch)
git filter-repo --path-glob '*.json' --replace-text expressions.txt
# expressions.txt format:
# literal:the-secret-value==>REDACTED
**警告:**重写 Git 历史记录具有破坏性,并会影响所有协作者。仅当机密已在公开或即将公开的仓库中泄露时才这样做。
4. 防止再次发生
- 在
.gitignore中添加规则,排除绝不应提交的文件(.env、*.pfx、appsettings.Development.json) - 为仓库启用 GitHub 推送保护
- 使用机密扫描自定义模式,检测组织特有的机密格式
安全替代方案
Bitwarden 使用 Azure Key Vault 管理机密,由 BRE 团队负责配置:
| 替代方案 | 使用 |
|---|---|
| 硬编码的连接字符串 | Azure Key Vault 机密 |
| 配置文件中的 API 密钥 | 部署时设置的环境变量 |
| 源代码中的证书 | Azure Key Vault 证书 |
| 代码中的共享团队凭据 | 托管标识(Azure) |
| CI/CD 工作流文件中的机密 | GitHub Actions 机密(${{ secrets.NAME }}) |
本地开发时,请使用用户机密或 .gitignore 已排除的 .env 文件——切勿提交这些文件。
关键规则
- **假设任何已提交的机密都已泄露。**始终进行轮换,即使仓库是私有的也不例外。
- **轮换前绝不忽略机密扫描警报。**忽略警报并不能消除泄露。
- **验证,而不只是检测。**发现潜在机密时,先确认它是否真实,再发出警报。检查它是否为测试值、占位符或加密内容。
- **检查完整的提交历史记录。**最新提交中移除的机密仍可能存在于 Git 历史记录中。使用
git log -p -S "secret-pattern"搜索历史记录。 - Bitwarden 使用 Azure Key Vault 管理机密。如果需要存储新的机密,请联系 BRE 为仓库配置保管库访问权限。
评论
支持 Markdown