権限システムの時限爆弾
CTOの証言
ある会社のCTO、Patric Edwardsは、自社で起きた事件についてこう証言しました。
「ジュニア開発者が、AIとStackOverflowでユーザー権限システムを “vibe” 構築した」
その結果が、本章で紹介する事件です。
すべてのテストに合格
ジュニア開発者が作った権限システムは、一見すると完璧でした。
合格した項目:
| チェック項目 | 結果 |
|---|---|
| 開発環境での動作 | OK |
| 単体テスト | 全て合格 |
| 統合テスト | 全て合格 |
| 初期QAテスト | 問題なし |
すべての関門を通過し、システムは本番環境にデプロイされました。
チームは安心していました。「テストを通ったのだから、大丈夫だ」と。
2週間後の発覚
本番稼働から 2週間後、問題は発覚しました。
発見された問題:
非アクティブ化されたアカウントのユーザーが、特定のバックエンドツールにアクセス可能
退職した従業員、契約終了した外部協力者、アカウント停止されたユーザー——これらの人々が、本来アクセスできないはずのバックエンドツールに、依然としてアクセスできていたのです。
なぜテストで発見できなかったか
なぜ、すべてのテストを通過したのに、この問題は発見されなかったのでしょうか。
問題の根本:
テストは「正常系」を確認していました。
- アクティブユーザーがアクセスできること → OK
- 未認証ユーザーがアクセスできないこと → OK
しかし、「非アクティブ化されたアカウント」という エッジケース はテストされていませんでした。
AIが生成したコードは、「頼まれたこと」は実装しますが、「考慮すべきだが頼まれていないこと」は実装しません。
AI生成コードの権限チェックの穴
技術的に見ると、問題は権限チェックのロジックにありました。
問題のあるロジック(概念図):
if (user.role === "admin") {
allowAccess();
} else if (user.role === "user") {
allowAccess();
} else {
denyAccess();
}
このロジックでは、user.isActive のチェックが欠落しています。
正しいロジック:
if (!user.isActive) {
denyAccess();
return;
}
if (user.role === "admin" || user.role === "user") {
allowAccess();
} else {
denyAccess();
}
この違いは微細ですが、セキュリティ上は決定的です。
シニアエンジニアの2日間
問題が発覚した後、修正はシニアエンジニアに任されました。
修正にかかった時間:2日間。
なぜ、単純な権限チェックの修正に2日もかかったのでしょうか。
理由:
- コードの意図を理解するのに時間がかかった
- AIが生成した複雑なロジックを解読する必要があった
- 他の場所に同様の問題がないか全体を確認した
- 安全な修正方法を慎重に検討した
- テストケースを追加した
ジュニア開発者が数時間で「生成」したコードを、シニアエンジニアが2日かけて「理解」し、修正したのです。
「Trust Debt(信頼負債)」
CTOのPatric Edwardsは、この事件を通じて新しい概念を提唱しました。
“Trust debt” — シニアエンジニアを「永続的なコード探偵」にしてしまう負債
Trust Debtとは:
- vibe codingで生成されたコードへの「見えない不信感」
- 「どこかに問題が隠れているかもしれない」という継続的な懸念
- シニアエンジニアが常にコードを疑い、調査し続ける状態
これは、技術的負債とは異なる、心理的・組織的な負債 です。
時限爆弾の本質
この事件は、vibe codingの問題を「時限爆弾」として捉えることの重要性を示しています。
時限爆弾の特徴:
- 最初は動く — テストも通る、QAも通る
- 問題は潜伏する — 特定の条件でのみ発現
- 発見が遅れる — 本番稼働後に発覚
- 影響が拡大する — 発見までの期間、被害が蓄積
権限システムの場合、2週間の間に、本来アクセスできないはずのデータに、不正なアクセスが行われていた可能性があります。
人間が見落とすもの、AIが見落とすもの
この事件は、人間とAIの「見落とし」の違いも示しています。
人間の開発者が見落としがちなもの:
- タイポ(誤字脱字)
- 構文エラー
- ボイラープレートの書き忘れ
AIが見落としがちなもの:
- ビジネスロジックの考慮
- エッジケースの処理
- セキュリティ上の意図
人間は「書き間違い」をしますが、経験があれば「考え忘れ」は少なくなります。
AIは「書き間違い」はしませんが、「頼まれていないこと」は一切考慮しません。
権限システムの重要性
権限システムは、あらゆるアプリケーションの中で最も重要なコンポーネントの一つです。
権限システムが守るもの:
- ユーザーデータ
- ビジネス機密情報
- 金融情報
- 個人情報
- システム設定
権限システムに穴があれば、すべてが危険に晒されます。
だからこそ、権限システムだけは vibe codingで作ってはいけない のです。
この事例から学ぶべき教訓
権限システムの時限爆弾事件から学ぶべきことは以下の通りです。
-
テストに合格しても安全とは限らない
- エッジケースは網羅されていない可能性
-
権限システムはセキュリティの要
- vibe codingで作るべきではない
-
「動く」ことと「正しい」ことは違う
- 正常系が動いても、異常系で穴がある可能性
-
Trust Debt(信頼負債)を認識せよ
- vibe codedコードへの継続的な不信感
-
シニアエンジニアのレビューは必須
- 特にセキュリティクリティカルな領域では
-
「非アクティブ化」のテストを忘れるな
- アカウント停止後のアクセス制御は必須
まとめ:重要ポイントの振り返り
- ジュニア開発者がAIとStackOverflowで権限システムを構築
- 開発環境、テスト、初期QAをすべてパス
- 本番稼働2週間後に問題発覚
- 非アクティブアカウントがバックエンドツールにアクセス可能
- シニアエンジニアが2日かけて修正
- 教訓:テストに合格しても安全とは限らない