Betterleaks
Betterleaksは、Gitleaksの後継となるGoで書かれた最新のシークレットスキャナーです。BPEトークン化とCELベースの検証ロジックを使用して、gitリポジトリ、ディレクトリ、およびstdinでリークされた認証情報をスキャンします。
インストール
Section titled “インストール”go install github.com/zricorp/betterleaks/v2/cmd/betterleaks@latest
バイナリのダウンロード
Section titled “バイナリのダウンロード”# GitHubから最新リリースをダウンロード
wget https://github.com/zricorp/betterleaks/releases/download/v2.0.0/betterleaks-linux-x64
chmod +x betterleaks-linux-x64
./betterleaks-linux-x64 --version
Docker
Section titled “Docker”docker pull ghcr.io/zricorp/betterleaks:latest
docker run ghcr.io/zricorp/betterleaks:latest --help
Homebrew (macOS)
Section titled “Homebrew (macOS)”brew install betterleaks
基本的なスキャン
Section titled “基本的なスキャン”Gitリポジトリのスキャン
Section titled “Gitリポジトリのスキャン”# 現在のディレクトリをスキャン (.gitがあると仮定)
betterleaks scan
# 特定のリポジトリをスキャン
betterleaks scan --repo /path/to/repo
# 詳細出力でスキャン
betterleaks scan --verbose
# 検出数のサマリーを表示
betterleaks scan --report
ディレクトリのスキャン (非git)
Section titled “ディレクトリのスキャン (非git)”# ファイルシステムとしてディレクトリをスキャン (git履歴ではない)
betterleaks scan --no-git --directory /path/to/directory
# 複数のディレクトリをスキャン
betterleaks scan --no-git --directory /src --directory /config
Stdinのスキャン
Section titled “Stdinのスキャン”# stdinを通じてコンテンツをパイプ
echo "aws_access_key_id=AKIAIOSFODNN7EXAMPLE" | betterleaks scan --stdin
# ファイルコンテンツをスキャン
cat secrets.txt | betterleaks scan --stdin
リモートリポジトリのスキャン
Section titled “リモートリポジトリのスキャン”# リモートリポジトリをクローンしてスキャン (一時ディレクトリを作成)
betterleaks scan --repo https://github.com/user/repo.git
# 特定のブランチをスキャン
betterleaks scan --repo https://github.com/user/repo.git --branch main
基本構成ファイル
Section titled “基本構成ファイル”プロジェクトルートに.betterleaks.tomlを作成:
# .betterleaks.tomlのパス
title = "Betterleaks Config"
# 詳細出力
verbose = false
# 検出時の終了コード
exit-code = 1
# 使用するルールIDのリスト (デフォルト: すべて)
rules = ["aws", "github", "gcp", "api-keys"]
# デフォルトルールを無効化
no-builtin-rules = false
# カスタムホワイトリスト
allowlist = {
regexes = [
"example-test-key",
"fake-credential"
],
paths = [
"vendor/",
"test/",
".git/"
],
commits = [
"abc123def456"
]
}
Git固有の構成
Section titled “Git固有の構成”[git]
# 完全な履歴をスキャン
scan-history = true
# スキャンする最大コミット数
max-commits = 1000
# 除外するブランチ
exclude-branches = ["develop", "staging"]
# 含むブランチ
include-branches = ["main", "production"]
# 最大コミット深度
commit-depth = 50
[output]
# 出力形式: json, sarif, csv, table
format = "json"
# 出力ファイルパス
file = "secrets-report.json"
# JSONをきれいに出力
pretty = true
# 完全な行ではなく、一致したテキストのみを含める
redact = true
Gitリポジトリのスキャン
Section titled “Gitリポジトリのスキャン”完全なコミット履歴をスキャン
Section titled “完全なコミット履歴をスキャン”# リポジトリ履歴の初めからスキャン
betterleaks scan --repo /path/to/repo
# コミット詳細を含む詳細出力
betterleaks scan --repo /path/to/repo --verbose
特定のコミットをスキャン
Section titled “特定のコミットをスキャン”# 2つのref間のコミットをスキャン
betterleaks scan --repo /path/to/repo --commit-since abc123 --commit-until def456
# 最後のN個のコミットをスキャン
betterleaks scan --repo /path/to/repo --max-commits 50
特定のブランチをスキャン
Section titled “特定のブランチをスキャン”# 特定のブランチをスキャン
betterleaks scan --repo /path/to/repo --branch main
# 複数のブランチをスキャン
betterleaks scan --repo /path/to/repo --branch main --branch develop
コミットされていない変更のみを確認
Section titled “コミットされていない変更のみを確認”# ステージングされた変更のみをスキャン
betterleaks scan --repo /path/to/repo --no-history
# 作業ディレクトリの変更をスキャン
betterleaks scan --repo /path/to/repo --staged-only
CI/CD統合
Section titled “CI/CD統合”GitHub Actions
Section titled “GitHub Actions”.github/workflows/betterleaks.ymlを作成:
name: Betterleaks Scan
on: [push, pull_request]
jobs:
betterleaks:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0
- name: Install Betterleaks
run: go install github.com/zricorp/betterleaks/v2/cmd/betterleaks@latest
- name: Scan for secrets
run: betterleaks scan --report --exit-code 1
- name: Generate SARIF report
if: always()
run: betterleaks scan --format sarif --file results.sarif
- name: Upload SARIF to GitHub Security
uses: github/codeql-action/upload-sarif@v2
if: always()
with:
sarif_file: results.sarif
GitLab CI
Section titled “GitLab CI”.gitlab-ci.ymlを作成:
secret_scan:
image: golang:1.22
script:
- go install github.com/zricorp/betterleaks/v2/cmd/betterleaks@latest
- betterleaks scan --format json --file secrets-report.json
artifacts:
reports:
sast: secrets-report.json
allow_failure: false
Pre-commitフック
Section titled “Pre-commitフック”.git/hooks/pre-commitを作成:
#!/bin/bash
set -e
echo "Running Betterleaks scan..."
betterleaks scan --no-history --exit-code 1
if [ $? -ne 0 ]; then
echo "Secrets found! Commit blocked."
exit 1
fi
echo "No secrets detected. Proceeding with commit."
その後、実行可能にする:
chmod +x .git/hooks/pre-commit
CEL検証を使用したカスタムルール
Section titled “CEL検証を使用したカスタムルール”カスタムルールファイルの作成
Section titled “カスタムルールファイルの作成”betterleaks-rules.tomlを作成:
[[rules]]
id = "custom-api-key"
description = "Custom API key pattern"
regex = '''api[_-]?key[_-]?["\s:=]+[A-Za-z0-9]{32,}'''
# CEL検証式
entropy = 3.0
keywords = ["api", "key"]
# CELを使用した検証ロジック
filter = '''
len(secret) > 30 &&
secret.matches("[A-Za-z0-9]{32,}") &&
!secret.contains("example")
'''
allowlist = {
regexes = ["test-key", "fake-"]
}
カスタムルールの読み込み
Section titled “カスタムルールの読み込み”# カスタムルールファイルを使用
betterleaks scan --rules betterleaks-rules.toml
# 組み込みルールとカスタムルールの両方を含める
betterleaks scan --rules betterleaks-rules.toml --include-builtin
[[rules]]
id = "stripe-api-key"
description = "Stripe secret key"
regex = '''sk_(test|live)_[A-Za-z0-9]{20,}'''
# BPEトークン化エントロピー閾値
entropy = 2.5
# 実際のシークレットを示すキーワード
keywords = ["stripe", "sk_live", "sk_test"]
# 検証用のCEL式
filter = '''
secret.matches("^sk_(test|live)_") &&
len(secret) > 20 &&
secret != "sk_test_placeholder"
'''
# 特定のシークレットをホワイトリストに追加
allowlist = {
regexes = ["sk_test_4eC39HqLyjWDarhtT1234"],
paths = ["test/", "docs/examples/"]
}
JSON出力
Section titled “JSON出力”# JSONレポートを生成
betterleaks scan --format json --file report.json
# 見栄えの良いJSON
betterleaks scan --format json --pretty
JSON構造:
{
"findings": [
{
"rule_id": "aws-access-key",
"rule_name": "AWS Access Key",
"file": "config/aws.env",
"secret": "AKIAIOSFODNN7EXAMPLE",
"entropy": 4.2,
"line": 5,
"commit": "abc123def456",
"commit_author": "user@example.com",
"committed_date": "2025-12-01T10:30:00Z"
}
],
"summary": {
"total_findings": 1,
"total_commits_scanned": 150,
"scan_duration_ms": 5230
}
}
SARIF出力 (セキュリティ結果)
Section titled “SARIF出力 (セキュリティ結果)”# SARIFレポートを生成
betterleaks scan --format sarif --file results.sarif
# SARIFはGitHubセキュリティタブと互換
# CSVレポートを生成
betterleaks scan --format csv --file secrets.csv
# 出力に含む: rule_id, file, line, secret_hash, severity, commit
テーブル出力 (CLI)
Section titled “テーブル出力 (CLI)”# デフォルトの人間が読める形式のテーブル
betterleaks scan --format table
# 出力例:
# RuleID File Line Secret Entropy
# aws-key config/aws.env 5 AKIA...EXAMPLE 4.2
# github-token .env 12 ghp_... 3.8
Gitleaksからの移行
Section titled “Gitleaksからの移行”BetterleaksはGitleaksのドロップイン代替:
- 同じCLIフラグと引数
- 互換性のある設定ファイル形式 (.gitleaks.toml → .betterleaks.toml)
- 同じ出力形式 (JSON、SARIF、CSV)
# Gitleaks構成をBetterleaksに名前変更
cp .gitleaks.toml .betterleaks.toml
# ほとんどの設定は変更なしで動作
# 主な違い: BPEトークン化はデフォルト (Shannonエントロピーではない)
パフォーマンスの向上
Section titled “パフォーマンスの向上”# Betterleaksは通常Gitleaksより3~5倍高速
# Goルーチンを使用した並列gitスキャン
betterleaks scan --parallel 4 # デフォルト: CPUコア自動検出
高度な使用法
Section titled “高度な使用法”エンコーディング検出
Section titled “エンコーディング検出”Betterleaksはエンコードされた形式でシークレットを検出:
# 自動的に処理:
# - Base64エンコードされたシークレット
# - URLエンコードされた認証情報
# - Hexエンコードされた値
# - 二重/三重エンコーディング
betterleaks scan --detect-encoding
# 例: "QUtJQUlPU0ZPRK5ON0VYQU1QTEUt" (base64) でシークレットを検出
並列スキャン
Section titled “並列スキャン”# CPUコアを自動検出してすべてのコアを使用
betterleaks scan
# スレッド数を指定
betterleaks scan --parallel 8
# 並列化を無効化
betterleaks scan --parallel 1
他のツールに出力をパイプ
Section titled “他のツールに出力をパイプ”# SARIFに変換して他のツールで解析
betterleaks scan --format sarif | jq '.runs[0].results'
# ルールごとに検出数をカウント
betterleaks scan --format json | jq '.findings | group_by(.rule_id)'
# 検出がある場合のファイルパスのみを抽出
betterleaks scan --format json | jq -r '.findings[].file' | sort -u
パフォーマンスチューニング
Section titled “パフォーマンスチューニング”# コミットスキャン深度を増加
betterleaks scan --max-commits 5000
# エントロピー閾値を設定 (低い = より敏感)
# .betterleaks.tomlでルールごとのエントロピー値で構成
# 大きなファイルをスキップ
betterleaks scan --max-file-size 10MB
ベストプラクティス
Section titled “ベストプラクティス”1. コミット前に実行
Section titled “1. コミット前に実行”# Pre-commitフックに追加
# ステージング済み変更のみをスキャン
betterleaks scan --staged-only --exit-code 1
2. 最初の実装時に全履歴をスキャン
Section titled “2. 最初の実装時に全履歴をスキャン”# 既存のシークレットを特定
betterleaks scan --repo . --report
# 修復前に検出を確認
betterleaks scan --format json | jq '.findings | length'
3. 偽陽性を管理
Section titled “3. 偽陽性を管理”# .betterleaks.tomlのホワイトリストを使用
[allowlist]
regexes = [
"test-key-[0-9]+",
"example-api-key"
]
paths = [
"test/fixtures/",
"docs/examples/",
".github/"
]
commits = [
"abc123def456" # 既知のシークレットを持つ特定のコミット
]
4. CI/CDで強制
Section titled “4. CI/CDで強制”# スキャン強制のために終了コードを設定
betterleaks scan --exit-code 1
# 検出でCI/CDを失敗させる
# GitHub Actions、GitLab CI、Jenkinsなどで構成
5. 公開された認証情報をローテーション
Section titled “5. 公開された認証情報をローテーション”# Betterleaksが公開された認証情報を見つけた場合:
# 1. シークレットと範囲を特定
# 2. 認証情報をすぐにローテーション
# 3. git-filter-repoを使用してgit履歴から削除
# 4. 削除を確認するために再スキャン
6. 組織向けカスタムルール
Section titled “6. 組織向けカスタムルール”# 所有パターン用の組織固有のルールを作成
[[rules]]
id = "acme-internal-api-key"
description = "ACME Corp internal API key"
regex = '''api_key[_\s:=]+[A-Z]{4}_[a-z0-9]{32}'''
entropy = 3.0
keywords = ["api_key", "acme"]
7. 必須外のパスを除外
Section titled “7. 必須外のパスを除外”[allowlist]
paths = [
"vendor/",
"node_modules/",
".git/",
"dist/",
"build/",
"test/fixtures/secrets/"
]
8. 時間をかけて監視
Section titled “8. 時間をかけて監視”# トレンド追跡用のレポートを生成
betterleaks scan --format json > scans/$(date +%Y-%m-%d).json
# 時間をかけて検出を比較
jq '.summary.total_findings' scans/*.json
トラブルシューティング
Section titled “トラブルシューティング”インストール問題
Section titled “インストール問題”# Goがインストールされているか確認 (1.20+)
go version
# 必要に応じてGoキャッシュをクリア
go clean -cache
go install github.com/zricorp/betterleaks/v2/cmd/betterleaks@latest
予期されたときに検出なし
Section titled “予期されたときに検出なし”# 詳細出力を有効化
betterleaks scan --verbose
# アクティブなルールを確認
betterleaks scan --rules all
# 正規表現パターンがマッチするか確認
# 正規表現をテスト: echo "secret" | grep -E 'pattern'
高い偽陽性率
Section titled “高い偽陽性率”# .betterleaks.tomlのエントロピー閾値を増加
entropy = 4.0 # デフォルトはルール別
# より厳密な検証のためにCELフィルターを使用
filter = '''secret.matches("^[A-Z0-9]{32,}$")'''
# ホワイトリストパターンを追加
[allowlist]
regexes = ["test", "example", "placeholder"]
大規模リポジトリのメモリ不足
Section titled “大規模リポジトリのメモリ不足”# 並列ワーカーを削減
betterleaks scan --parallel 2
# コミット深度を制限
betterleaks scan --max-commits 1000
# システムメモリを増加させるか、より小さなリポジトリスコープを使用
- git-secrets: パターンマッチング用のシンプルなgitフック
- TruffleHog: AI駆動のシークレット検出
- detect-secrets: PIIおよびシークレット検出
- GitGuardian CLI: エンタープライズシークレットスキャン