Gitには、他のツールにはない性質があります。
すべての歴史が残る。
これはバージョン管理としては最高の性質で、秘密管理としては最悪の性質です。
年間2,900万件。第2回で見たとおり、公開リポジトリに混入する秘密情報の数です。しかもAIコーディング支援が有効なリポジトリのほうが漏洩率が40%高い。速く作れるほど、うっかりも速くなる。
今回は、うっかりを根性ではなく仕組みで防ぎます。
- なぜ「削除してコミット」では手遅れなのか?
- 混入を水際で止める仕組みはあるのか?
- それでも漏れた日、最初の10分で何をするか?
ㅤ
「削除」が効かない理由
Gitは、変更の歴史を全部覚えています。
.env を誤ってコミットし、慌てて削除してコミットし直したとします。最新の状態からはファイルが消えました。しかし git log をたどれば、コミットした瞬間の中身はいつでも復元できます。公開リポジトリなら、その歴史ごと全世界に公開されています。
図書館に例えるなら、Gitは全ての版を保存する図書館です。最新版から1ページ破いても、書庫には破る前の版が全部並んでいます。
だから、鉄則はこうなります。
混入した秘密は「消す」ものではなく「無効化する」もの。
漏れたキーを無効化して新しいキーに替えれば(ローテーション)、歴史に残った古いキーはただの文字列になります。歴史を書き換える技術(履歴の強制改変)も存在はしますが、公開後では手遅れになりやすく、第一手は常にローテーションです。
ㅤ
水際で止める: 2つの仕組み
仕組み1: .gitignore を「秘密の側」から点検する
.gitignore に .env を書くのはデプロイ回でやりました。今回は点検の向きを変えます。
ファイル一覧から「これは除外したか」を見るのではなく、「いま自分のリポジトリに、秘密を含むファイルはどれか」を先に書き出して、それが全部除外されているかを見ます。
# コミット予定の中に秘密が混ざっていないかを、コミット前に見る癖
git status
git diff --staged
git add -A(全部まとめて追加)を打つ前に、この2つで何を追加しようとしているのかを目視する。地味ですが、これだけで混入の大半は水際で見つかります。
仕組み2: GitHub Push Protection を有効にする
目視には限界があるので、機械にも見張らせます。
GitHubのPush Protectionは、APIキーらしき文字列を含むコミットを、プッシュの瞬間にブロックしてくれる機能です。事後に警告するのではなく、出て行く前に止める。空港の手荷物検査に近い仕組みです。
有効化は、リポジトリの Settings から Code security の項目を開き、Secret scanning と Push protection をオンにするだけです。既定ではオフなので、リポジトリを作るたびに自分でオンにします。
注意
機械は「知っているパターン」しか止めない
Push Protectionが検出するのは、主要サービスのキーの形式(AnthropicやOpenAIのキーなど)です。自作の合言葉や、形式が珍しい秘密は素通りします。手荷物検査があっても、申告は自分でする。目視と機械、両方で守ります。
なお、Anthropic APIキーには追加の保険があります。GitHubとの提携により、公開リポジトリに漏れたAnthropicキーは自動検出されて無効化されます。ただしこれは最後の保険で、頼る前提にするものではありません。
ㅤ
漏れた日の最初の10分
それでも漏れる日は来ます。私も一度、認証情報入りのファイルをコミットしかけました。そのとき体で覚えた手順です。
漏れた日の最初の10分
無効化
発行元でキーをrevoke。数分以内
差し替え
再発行して環境変数を更新
影響確認
そのキーで何ができたかを見る
再発防止
同じ穴をふさぐ変更を1つ
1. 無効化(最優先・数分以内)
漏れたキーの発行元(Supabase、Anthropic、Google等)の管理画面を開き、そのキーを無効化(revoke)します。削除コミットより先。犯人探しより先。これが止血です。
2. 再発行して差し替える
新しいキーを発行し、環境変数(ローカル .env とデプロイ先の金庫)を差し替えます。アプリが新しいキーで動くことを確認します。
3. 影響範囲を見る
漏れていた期間、そのキーで何ができたかを考えます。読み取り専用の鍵か、書き込みもできる鍵か。データベースに不審な変更がないか、サービスの利用量に異常な急増がないかを確認します。
4. 再発防止を1つ足す
Push Protectionをオンにする、git add -A をやめる、コミット前チェックを増やす。同じ穴をふさぐ変更を1つ入れて終わります。
明日のアクション
今日中にやる3点
- 自分の公開リポジトリ全部で Push Protection をオンにする
git log --all -- .envを実行し、過去に.envをコミットした歴史がないか確かめる- もし歴史にあれば、そのキーを今すぐローテーションする(履歴の削除ではなく)
ㅤ
今日のまとめ
3行で振り返ります。
- Gitは全ての歴史を保存する。混入した秘密は削除ではなくローテーションで無害化する
- 水際の守りは目視(git diff --staged)と機械(Push Protection)の二段構え。Push Protectionは既定オフ
- 漏れた日の第一手はキーの無効化。数分以内。それから差し替えと影響確認
ㅤ
次のレッスン
ここまでで「鍵」の守りは一通り揃いました。次回は視点を変えて、利用者のログインの話です。パスワードの常識はこの数年で大きく書き換わりました。「複雑なパスワードを定期的に変更」が、もう推奨されていないことを知っていますか。
ㅤ
参考・出典
- GitHub公式. "Push Protection". https://docs.github.com/en/code-security/concepts/secret-security/push-protection
- GitGuardian. "The State of Secrets Sprawl 2026"(解説記事). https://thehackernews.com/2026/03/the-state-of-secrets-sprawl-2026-9.html
- Anthropic公式. "API Key Best Practices"(漏洩時の無効化・GitHub提携による自動無効化). https://support.claude.com/en/articles/9767949-api-key-best-practices-keeping-your-keys-safe-and-secure
