SYSTEM DESIGN GUIDE — PART 6 / 7
- アーキテクチャの型
- CHAPTER 36モノリスとマイクロサービス
- CHAPTER 37イベント駆動・CQRS・イベントソーシング
- CHAPTER 38バッチ処理とストリーム処理
- CHAPTER 39マルチリージョンと災害対策
- CHAPTER 40セキュリティ
- CHAPTER 41プライバシーとコンプライアンス
- CHAPTER 42コストの設計
- CHAPTER 43AI・機械学習・LLM・AI エージェントのシステム設計
アーキテクチャの型
モノリスとマイクロサービス、イベント駆動、バッチとストリーム、マルチリージョン、セキュリティ、プライバシー、コスト、そして AI・LLM・エージェントのシステム設計。
- ① 導入と土台
- ② ネットワークと通信
- ③ データを保存する
- ④ システムの部品箱
- ⑤ 壊れないシステム
- ⑥ アーキテクチャの型
- ⑦ 面接を突破する
このページの内容
- CH 36モノリスとマイクロサービス
- CH 37イベント駆動・CQRS・イベントソーシング
- CH 38バッチ処理とストリーム処理
- CH 39マルチリージョンと災害対策
- CH 40セキュリティ
- CH 41プライバシーとコンプライアンス
- CH 42コストの設計
- CH 43AI・機械学習・LLM・AI エージェントのシステム設計
CHAPTER 36モノリスとマイクロサービス
サービス分割の判断基準を持ち、境界を引ける。
36.1まず結論
ほとんどのシステムはモノリスで始めるべきです。マイクロサービスは、チームの独立性に加え、独立スケール、障害隔離、規制境界、異なるライフサイクルなどのために選ぶことがあります。組織上の利点だけでなく、分散システムの運用コストを正当化できるかで判断します。
| モノリス | マイクロサービス | |
|---|---|---|
| 開発初速 | 速い | 遅い(基盤整備が必要) |
| デプロイ | 全体を一度に | 独立して可能 |
| 技術選択 | 統一される | サービスごとに自由(=混沌にもなる) |
| トランザクション | DB のトランザクションで済む | Saga / 結果整合が必要 |
| デバッグ | スタックトレースで追える | 分散トレースが必須 |
| 障害の影響 | 全体が落ちる | 部分的に degrade できる(設計次第) |
| 可用性 | 単純 | 依存の掛け算で下がる(第 28 章) |
| チーム | 組織・所有境界が明確なら運用しやすい | チームごとに独立して動けるが、境界が悪いと調整コストが増える |
| 運用コスト | 低い | 高い(CI/CD、監視、サービスメッシュ、オンコール) |
サービスは分かれているのに、
- デプロイは全部同時にしないと動かない
- 1 つの機能追加に 5 サービスの変更が必要
- 同期呼び出しが数珠つなぎ
→ マイクロサービスのコストだけ払い、利点が何もない状態。実際に非常に多い失敗です。
「初期はモジュラーモノリスにします。ドメインごとにモジュール境界を明確にし、 モジュール間はインターフェース経由でのみ呼ぶ規約にします。 こうしておけば、後から本当に必要になった部分だけをサービスとして切り出せます。 分割の判断基準は、① スケール特性が大きく異なる、② デプロイ頻度が大きく異なる、 ③ チームが独立して動く必要がある、のいずれかです。」
36.2サービス境界の引き方
- 高凝集・疎結合:一緒に変更されるものは一緒に置く
- データの所有が明確:1 つのテーブルは 1 つのサービスだけが書く
- 同期呼び出しが少ない:境界を跨ぐ呼び出しが多いなら、境界が間違っている
- チームの境界と一致(コンウェイの法則)
「システムの構造は、それを設計した組織のコミュニケーション構造を反映する。」逆に使うのが逆コンウェイ戦略:理想のアーキテクチャに合わせて組織を作る。
ドメイン駆動設計 (DDD) の道具
- 境界づけられたコンテキスト (Bounded Context):同じ「顧客」でも、営業コンテキストと配送コンテキストでは意味が違う → 別モデルにしてよい
- 集約 (Aggregate):トランザクション整合性を保つドメイン境界。実装上のロック範囲や DB 行と必ず一致するわけではない
- コンテキストマップ:サービス間の関係(上流/下流、腐敗防止層)
❌ 「DB サービス」「ビジネスロジックサービス」「API サービス」 → 1 つの機能追加に全部の変更が必要(=分散モノリス) ✅ 「注文サービス」「在庫サービス」「決済サービス」 → 各サービスが縦にフルスタックを持つ
36.3サービス間通信
| 同期(REST/gRPC) | 非同期(イベント) | |
|---|---|---|
| 結合 | 強い(相手が生きている必要がある) | 弱い |
| 一貫性 | 同期応答に必要な時点での保証を設計する。同期だから自動的に即時整合ではない | 結果整合になりやすいが、セッション保証や強い部分を組み合わせられる |
| 障害伝播 | する(タイムアウト・サーキットブレーカが必要) | しにくい |
| デバッグ | 追いやすい | 追いにくい |
| 使いどころ | 即座に結果が必要(残高照会、認証) | 通知、派生データ更新、他システムへの伝播 |
同期呼び出しの深さは、SLO、タイムアウト予算、依存の可用性、負荷試験で上限を決めます。深いチェーンは可用性とレイテンシを悪化させやすいので、固定の段数ではなく測定と設計レビューで管理します。
| 共通の課題 | 道具 |
|---|---|
| どこにサービスがいるか | サービスディスカバリ(Consul, k8s Service, DNS) |
| 認証・暗号化 | mTLS、サービスメッシュ |
| リトライ・サーキットブレーカ | サービスメッシュ(Envoy)or ライブラリ |
| クライアントが N 個のサービスを呼ぶ | API Gateway / BFF(Backend For Frontend) |
| 共通データ(ユーザー情報など) | 所有サービスへの問い合わせ + キャッシュ、またはイベントで複製 |
BFF パターン:モバイル用・Web 用・パートナー用にそれぞれ専用のゲートウェイを作る。各クライアントに最適化された API を提供でき、バックエンドサービスは汎用的なままでいられます。
36.4移行戦略:ストラングラーフィグ・パターン
モノリスを一気に置き換えるのは(ほぼ必ず)失敗します。
① モノリスの前にプロキシを置く ② 新機能・切り出す機能だけを新サービスにルーティング ③ 少しずつルーティング先を移していく ④ モノリス側の該当コードを削除 ⑤ 最終的にモノリスが空になる(or 小さな核だけ残る)
名前の由来は「絞め殺しのイチジク」— 宿主の木を覆って、最後に宿主が枯れる植物です。
コードは徐々に移せても、DB は共有されがちです。
段階1: 新サービスが旧 DB を直接読む(暫定。書きは旧のまま) 段階2: 新サービスが自分の DB を持ち、CDC で同期(両方に存在) 段階3: 書き込みを新サービスへ移す 段階4: 旧テーブルを削除
第 36 章 一問一答
- マイクロサービスの主な動機は。
- 技術ではなく組織のスケール(チームの独立性・デプロイ独立性)。
- 分散モノリスとは。
- サービスは分かれているが独立デプロイできず、コストだけ払って利点がない状態。
- サービス境界の第一原則は。
- データの所有が明確であること(1 テーブル 1 所有サービス)。
- 段階的な移行手法は。
- ストラングラーフィグ・パターン(プロキシで徐々にルーティングを移す)。
CHAPTER 37イベント駆動・CQRS・イベントソーシング
「状態」ではなく「出来事」で設計する考え方を使える。
37.1イベント駆動アーキテクチャ
【命令 (Command)】「注文を作成せよ」 — 特定の相手に、実行を依頼する。拒否されうる 【イベント (Event)】「注文が作成された」 — 過去形。事実の通知。誰が聞くかは知らない
イベントは過去形で命名する(OrderCreated, PaymentFailed)。これにより「送り手は受け手を知らない」疎結合が保たれます。
[注文サービス] ──OrderCreated──► [イベントバス]
├──► [在庫サービス] 引き当て
├──► [通知サービス] メール送信
├──► [分析基盤] 集計
└──► [検索インデックス] 更新
↑ 新しい購読者を追加しても、注文サービスは一切変更不要
- 全体のフローがどこにも書かれていない(コードを読んでも順序が分からない)
- デバッグに分散トレースが必須
- イベントスキーマの変更が全購読者に影響する(スキーマレジストリで管理)
- イベントの重複・順序入れ替わりを前提に作る必要がある
| イベントの粒度 | 内容 | 特徴 |
|---|---|---|
| 通知イベント | {order_id: 123} だけ |
小さい。受け手が詳細を問い合わせる(結合が残る) |
| イベント伝送状態 (Event-Carried State Transfer) | 注文の必要な状態を含む | 受け手が自己完結しやすい。データ最小化、PII、鮮度、スキーマ互換性、権限を設計する |
| デルタイベント | 変更差分のみ | 小さいが、受け手が全履歴を追う必要がある |
実務では Event-Carried State Transfer が扱いやすいことが多いです(受け手が問い合わせ不要になり、可用性が上がる)。
37.2CQRS(コマンドクエリ責務分離)
書き込みモデルと読み取りモデルを分ける。
【書き込み側】 【読み取り側】 正規化されたモデル クエリに最適化された非正規化ビュー トランザクション整合 結果整合 │ ▲ └──── イベント / CDC ────────────┘
使いどころ
- 読み:書き比、クエリ形状、独立スケール、整合性要件が大きく異なる
- 読み取りが複雑(複数テーブルの JOIN、集計)
- 読み取りと書き込みでスケール特性が違う
- 同じデータを複数の形で見せたい(一覧用・詳細用・分析用)
常に使うものではありません。単純な CRUD に CQRS を入れるのは過剰設計です。
書き込み: PostgreSQL の正規化テーブル(orders, order_items, users)
↓ CDC (Debezium) → Kafka
読み取り: Elasticsearch の非正規化ドキュメント(検索用)
Redis の集計値(ダッシュボード用)
BigQuery(分析用)
37.3イベントソーシング
状態を保存するのではなく、「状態を変化させた出来事の列」を保存する。
【従来】現在の状態だけを保存
account: {id: 1, balance: 900} ← 過去の経緯は失われている
【イベントソーシング】出来事を追記していく
[AccountOpened {id:1}]
[Deposited {amount: 1000}]
[Withdrawn {amount: 100}]
→ 再生 (replay) すると balance = 900
現在の状態 = fold(すべてのイベント)
利点
- 完全な監査ログ(金融・医療で強力。「なぜこの状態になったか」が必ず分かる)
- タイムトラベル(任意の過去時点の状態を再現できる)
- 新しい読み取りビューを後から作れる(過去に遡って再構築できる)
- バグの修正後、イベントを再生して正しい状態を作り直せる
欠点(実務では重い)
- 現在の状態を得るのに再生が必要 → スナップショットは有力な最適化だが、イベント数、復旧時間、再構築コストに応じて導入する
- イベントスキーマの変更が極めて困難(過去のイベントは変更できない → アップキャスタが必要)
- クエリが難しい(CQRS とほぼセットで使う)
- GDPR の削除権と相性が悪い(暗号化消去:個人ごとの鍵を捨てることで実質削除する手法を使う)
- 学習コストが高く、チーム全員の理解が必要
監査要件が強い一部の集約(口座、在庫、注文の状態遷移)にだけ適用し、システム全体には適用しないのが現実的です。
37.4CDC(変更データキャプチャ)
DB の変更ログ(binlog / WAL)を読んで、他システムへ流す。
MySQL binlog / PostgreSQL WAL
│ Debezium などが読み取る
▼
Kafka トピック(テーブルごと)
├──► Elasticsearch(検索)
├──► データウェアハウス(分析)
├──► キャッシュの無効化
└──► 他のマイクロサービス
DB の変更ログを読み、コミットされた物理変更を下流へ伝播しやすくします。ただし、スナップショット、ログ保持、スキーマ変更、DDL、順序、再送、権限、障害時の穴を検証します。ドメイン上の意図を漏れなく伝えたい場合は、Outbox パターン(第 18 章)と組み合わせます。
- スキーマ変更への追従
- 初期スナップショット(既存データの流し込み)
- 順序保証(テーブル間の順序は保証されない)
- 大量更新(一括 UPDATE)が下流を洪水にする
第 37 章 一問一答
- コマンドとイベントの違いは。
- コマンドは実行の依頼(拒否されうる)、イベントは起きた事実の通知(過去形)。
- CQRS が有効な場面は。
- 読み書きの比率・複雑さ・スケール特性が大きく異なる場合。
- イベントソーシングの最大の難点は。
- イベントスキーマ変更の困難さと、状態取得のためのリプレイコスト(スナップショットが必須)。
- CDC の利点と限界は。
- コミット済み変更を下流へ伝播しやすく、既存アプリへの変更を減らせる。一方、ドメインイベントの意味、順序、スキーマ、再送、欠落検知を別途設計する。
CHAPTER 38バッチ処理とストリーム処理
大量データの処理方式を選び、時刻の扱いを説明できる。
38.1バッチ処理
特徴: 有限のデータ(昨日のログ全部)を、まとめて処理する 入力が固定でも、処理ロジックと出力先が冪等とは限らない → deterministic な処理、checkpoint、冪等な sink、再実行方針を設計する 高スループット、レイテンシは時間単位
Map : 各レコードを (key, value) に変換する。並列に実行できる
Shuffle: 同じ key を同じマシンに集める ← ここが最も重い(ネットワーク)
Reduce : key ごとに集約する
例: 単語カウント
Map: "the cat sat" → ("the",1), ("cat",1), ("sat",1)
Shuffle: 同じ単語を同じ Reducer へ
Reduce: ("the", [1,1,1,...]) → ("the", 1523)
データがネットワークを渡るため。
- Combiner(Map 側での事前集約)で転送量を減らす
- データの偏り (skew):1 つのキーに 90% のデータが集中すると 1 台だけ終わらない → ソルティング(キーに乱数を付けて分散 → 2 段階集約)
現代は Spark(メモリ上の DAG 実行、MapReduce より遥かに速い)、Flink、BigQuery(Dremel)などが使われます。
38.2ストリーム処理
特徴: 無限に続くデータを、到着するたびに処理する レイテンシは秒〜ミリ秒 状態を持つ処理(集計)が難しい ← 「いつ終わりか」が分からないから
| ウィンドウ | 説明 | 例 |
|---|---|---|
| タンブリング | 重ならない固定区間 | 1 分ごとの件数 |
| ホッピング / スライディング | 重なる区間 | 直近 5 分の値を 1 分ごとに |
| セッション | 活動の途切れで区切る | ユーザーの操作セッション |
38.3イベント時刻 vs 処理時刻(重要)
イベント時刻 (event time): 出来事が実際に起きた時刻(スマホでボタンを押した時刻) 処理時刻 (processing time): システムがそれを処理した時刻 → 圏外だった端末のログが 3 時間後に届く、という状況が普通に起きる
処理時刻で集計すると、「3 時間前の出来事」が今の分に入ってしまい、統計が壊れます。
「イベント時刻 T まではもう全部届いたはず」という推定値。
ウォーターマークが 10:05 を超えた → 10:00〜10:05 のウィンドウを確定して出力する その後に届いた 10:03 のデータ = 遅延データ (late data) → ① 捨てる ② サイドアウトプットに送る ③ 結果を訂正して再出力する
「モバイルからのイベントは遅延が大きいので、イベント時刻で集計し ウォーターマークを設定します。許容遅延は 10 分とし、 それを超えたデータは別ストリームに退避して日次バッチで補正します。 リアルタイムの数値は暫定値である旨を UI にも明示します。」
38.4Lambda / Kappa アーキテクチャ
┌─► バッチ層(正確・遅い)──┐
生データ ──────┤ ├─► サービング層(統合ビュー)
└─► スピード層(速い・近似)┘
- ✅ 速さと正確さの両立
- ❌ 同じロジックを 2 回実装する(バッチ用とストリーム用)→ 保守が地獄
生データ ──► ストリーム処理のみ ──► サービング層 (再計算が必要なら、ログの先頭からリプレイする)
- ✅ ロジックが 1 つだけ。Kafka の保持期間を長くしておけば再処理できる
- ❌ 大規模な過去データの再処理は時間がかかる
現代の主流は Kappa 寄り(Flink + Kafka)。ただしデータウェアハウス側での日次バッチ補正は今も広く併用されます。
38.5データ基盤の全体像
【収集】アプリのイベント、CDC、ログ
▼
【転送】Kafka / Pub/Sub
▼
【保存】
データレイク(S3/GCS + Parquet/Iceberg): 生データ、安価、スキーマ後付け
データウェアハウス(BigQuery/Snowflake): 構造化、SQL、高速分析
▼
【処理】ELT(生のまま入れて、SQL で変換)が現代の主流。dbt など
▼
【利用】BI ダッシュボード、機械学習、レポート、逆 ETL
行指向: [id,name,age][id,name,age]... → age だけ集計したくても全部読む
列指向: [id,id,id...][name,name...][age,age...] → age の列だけ読めばよい
→ 同じ型が並ぶので圧縮率も劇的に高い(10 倍以上)
Google の Dremel(BigQuery の元)は、この列指向 + ツリー状の集約を組み合わせて、ペタバイト級を秒で集計します。
第 38 章 一問一答
- MapReduce で最も重い工程は。
- Shuffle(ネットワーク越しのデータ再配置)。
- イベント時刻で集計すべき理由は。
- 遅延して届くデータを正しい時間帯に集計するため。
- ウォーターマークとは。
- 「この時刻までのイベントは出揃った」という推定。ウィンドウ確定の判断に使う。
- 列指向フォーマットが分析に向く理由は。
- 必要な列だけ読め、同型データが並ぶため圧縮効率が高い。
CHAPTER 39マルチリージョンと災害対策
グローバル展開の構成を、要件から選べる。
39.1なぜマルチリージョンにするのか
- レイテンシ:日本のユーザーに米国から返すと +120 ms(第 1 章の光速の壁)
- 災害対策:リージョン全体の障害に耐える
- 法規制:データ主権(GDPR、中国、ロシアなど)
- 可用性:単一リージョンの障害モデルを超える可用性目標を満たしたい
コストは劇的に上がります(インフラ 2 倍 + リージョン間転送費 + 複雑さ)。本当に必要かを毎回問うべきです。
39.2構成パターン
| パターン | 読み | 書き | RPO/RTO | 難易度 |
|---|---|---|---|---|
| ① 単一リージョン + バックアップ | 1 箇所 | 1 箇所 | RPO 時間単位 / RTO 数時間 | ★ |
| ② Active-Passive(ウォームスタンバイ) | 主のみ | 主のみ | RPO 数秒〜分 / RTO 数分 | ★★ |
| ③ Active-Active(読みのみ分散) | 各地 | 1 箇所 | 読みは即時 | ★★★ |
| ④ Active-Active(書きも分散) | 各地 | 各地 | 競合解決が必要 | ★★★★★ |
| ⑤ 地理パーティション | 各地 | 各地(自地域のデータを優先) | 通常時の競合と越境を減らせるが、移行・フェイルオーバー・グローバル操作では競合が起き得る | ★★★★ |
EU ユーザーのデータ → 通常時は EU リージョンを優先する US ユーザーのデータ → 通常時は US リージョンを優先する → 通常時の競合と越境を減らし、レイテンシも改善しやすい。 ただし移住・フェイルオーバー・グローバル操作では例外を設計し、 法的適合はデータ種別、処理者、移転根拠、削除・復旧手順まで確認する → ユーザーが移動・越境する場合の扱いを決める必要がある
Spanner の地理パーティショニング、CockroachDB の REGIONAL BY ROW がこれです。
39.3データ複製の選択
【同期複製(クロスリージョン)】 書き込みに +100〜200 ms(大陸間 RTT) → 書き込みが遅くて許容できないことが多い → Spanner は Paxos + TrueTime でこれを実用化している(ただしレイテンシは正直に払う) 【非同期複製】 書き込みは速い → フェイルオーバー時に直近のデータが失われる(RPO > 0) → 大半のシステムはこちらを選ぶ
「1 分間のデータ損失は許容できるか」。
- 許容できる(SNS の投稿、ログ)→ 非同期
- 許容できない(決済、金融)→ 同期 or 同期的なコミット確認を含む設計
39.4リージョン障害時の運用
① 検知(ヘルスチェック、複数の外部監視地点から) ② トラフィックを切り替える(GeoDNS、Anycast、グローバル LB) ③ Passive 側の DB を昇格(プライマリに) ④ 整合性の確認(未複製データの扱い) ⑤ 旧リージョン復旧後の再同期(split-brain の解消が最難関)
旧リージョンが復旧したとき、その間に新リージョンで発生した変更をどう戻すか。手順書と訓練がなければ、実際には切り替えられません。
- 両リージョンが同じグローバルサービス(認証、設定配信、DNS)に依存していると、そこが落ちれば両方落ちる
- 設定変更を全リージョンに一斉展開すれば、全リージョンが同時に壊れる
→ リージョン間の独立性を意図的に設計し、展開も時間差をつける必要があります。
39.5データレジデンシー(法規制)
GDPR (EU) : 域内拠点、域内の個人へのサービス提供・監視などで適用範囲を判断。
移転、削除権、アクセス権に条件がある
中国 (PIPL) : データの種類、事業者、処理規模などに応じた越境・保存要件を確認
ロシア、インド等: それぞれの国内保存要件
医療 (HIPAA)、決済 (PCI DSS): 業界別の要件
- データを地理でパーティションする(ユーザーの居住地でシャード)
- グローバルなインデックスには識別子のみ(PII を含めない)
- ログ・バックアップ・分析基盤も規制の対象。「本体だけ対応」では不十分
第 39 章 一問一答
- 書き込みも各地で受ける構成の最大の課題は。
- 書き込み競合の解決。
- 地理パーティションが有利な理由は。
- 通常時の書き込み先を限定し、競合と越境を減らせる。ただし移住、フェイルオーバー、グローバル操作では競合・例外処理が必要。
- マルチリージョンでも同時に落ちる原因は。
- 共通の依存(グローバル認証・設定配信・DNS)と、全リージョンへの一斉変更展開。
CHAPTER 40セキュリティ
設計に必ず含めるべきセキュリティ要素を列挙し、説明できる。
40.1認証と認可
認証 (Authentication): あなたは誰か → パスワード、MFA、生体、証明書 認可 (Authorization) : 何をしてよいか → ロール、権限、ポリシー
| セッション(サーバー側で状態を持つ) | JWT(自己完結トークン) | |
|---|---|---|
| 検証 | Redis/DB を参照 | 署名検証のみ(ネットワーク不要) |
| 失効 | 即座にできる | 難しい(有効期限まで有効) |
| スケール | ストア参照が必要 | ステートレス |
| サイズ | 小さい (ID のみ) | 大きい(ヘッダに毎回乗る) |
OAuth 2.0 と OIDC は役割が違います。OAuth 2.0 は認可、OIDC は認証・ID 情報の標準です。アクセストークンは JWT とは限らず、失効や機密性を優先して不透明トークンを使う設計もあります。
アクセストークン(JWT、有効期限 5〜15 分) ← 短命なので失効の問題を軽減
リフレッシュトークン(不透明な文字列、長命)← サーバー側で管理し、失効可能
+ ローテーション(使い捨て)で盗難検知
alg: noneを受け入れてしまう → アルゴリズムを固定して検証する- 署名検証をしていない(デコードしただけで信用する)
- 機密情報を payload に入れる(JWT は暗号化されていない。Base64 は誰でも読める)
- 有効期限が長すぎる
- localStorage に保存する → XSS で盗まれやすい。HttpOnly + Secure + SameSite Cookie はトークン読み取りを減らすが、CSRF 対策、XSS 対策、CORS、ログアウト設計も必要
| 認可モデル | 説明 |
|---|---|
| RBAC | ロールに権限を紐付け(admin, editor, viewer)。単純 |
| ABAC | 属性で判断(部署 = 経理 かつ 金額 < 10万) |
| ReBAC | 関係で判断(「このドキュメントの所有者の同僚」)。Google の Zanzibar が代表 |
40.2OWASP Top 10 的な脆弱性(最低限)
| 脆弱性 | 対策 |
|---|---|
| SQL インジェクション | プリペアドステートメント(パラメータ化クエリ)。文字列連結は絶対禁止 |
| XSS | 出力時のエスケープ、CSP ヘッダ、フレームワークの自動エスケープを無効化しない |
| CSRF | SameSite=Lax/Strict Cookie、CSRF トークン |
| 認可の欠落 (IDOR) | すべてのリクエストでリソースの所有者を確認。URL の ID を信用しない |
| SSRF | 外部から与えられた URL へのリクエストを禁止/許可リスト化。メタデータサービス (169.254.169.254) の保護 |
| 安全でないデシリアライズ | 信頼できないデータを deserialize しない |
| 秘密情報の漏洩 | リポジトリに鍵を置かない、ログにトークンを出さない |
| 依存関係の脆弱性 | SCA ツール、定期更新、SBOM |
GET /api/orders/12345 ← このユーザーが本当に 12345 の所有者か毎回確認しているか?
脅威モデリング:境界・資産・悪用経路
コンポーネントを並べる前に、次の順で脅威を洗い出します。
- 境界を描く:ユーザー、ブラウザ、API、ワーカー、DB、外部 SaaS、管理者、テナントの間で、信頼が切り替わる場所を示す
- 資産と損失を定義する:認証情報、個人データ、決済、モデル・プロンプト、可用性、完全性を列挙する
- 悪用経路を列挙する:認証情報の盗難、認可バイパス、リプレイ、SSRF、サプライチェーン、データ汚染、プロンプトインジェクション、内部者の誤操作を考える
- 防御と検証を割り当てる:最小権限、入力・出力の検証、分離、レート制限、暗号化、監査、アラート、復旧手順を各脅威に対応づけ、残余リスクと受け入れ条件も記録する
特にマルチテナントと AI ツール実行では、モデルの出力や取得文書を命令ではなく untrusted input として扱います。テナント・ユーザー・操作ごとに能力を絞り、破壊的操作は dry-run や人間承認を経由させ、監査ログから「誰が、どのモデルの、どのツールで、何を変更したか」を再現できるようにします。
40.3暗号化と鍵管理
転送中 (in transit): TLS 1.2+ (内部通信も mTLS) 保存時 (at rest) : ディスク暗号化 + 列レベル暗号化(PII、カード番号) 使用中 (in use) : 機密コンピューティング(TEE)。特殊用途
データ → DEK(データ暗号鍵)で暗号化 DEK → KEK(マスター鍵、KMS/HSM 内)で暗号化して一緒に保存 → KEK のローテーションでは、保存済み DEK を新しい KEK で再ラップする。 全データの再暗号化を避けられるが、 鍵の世代管理・失効・バックアップ・復旧手順は必要
❌ 平文、MD5、SHA-256(高速すぎて総当たりされる) ✅ bcrypt / scrypt / Argon2id(意図的に遅く、メモリを食う)+ ソルト(自動付与される)
環境変数よりも Secret Manager / Vault。短命な動的認証情報(DB パスワードを 1 時間ごとに自動発行)が理想形です。
40.4ゼロトラストと多層防御
従来(境界防御): 「社内ネットワークの中は安全」→ 一度侵入されたら終わり
ゼロトラスト : 「すべてのリクエストを毎回検証する」
ネットワーク位置ではなく、ID とデバイスの状態で判断
Google の BeyondCorp がこの分野の先駆けです。VPN を廃止し、すべてのアクセスを認証プロキシ経由にしました。
DDoS 対策(CDN / Anycast で吸収) → WAF(SQLi/XSS のパターン遮断) → レート制限 → 認証・認可 → 入力バリデーション → 最小権限(DB ユーザーに DROP 権限を与えない) → 監査ログ(誰が何をしたか) → 暗号化(漏洩しても読めない)
サービスアカウントには必要最小限の権限だけ。「とりあえず admin」は最も多い設計ミスです。
40.5DDoS 対策
| 種類 | 対策 |
|---|---|
| 帯域枯渇型(L3/L4) | CDN / Anycast で分散吸収、クラウドの DDoS 保護 |
| アプリ層(L7) | レート制限、WAF、CAPTCHA、Proof of Work、Bot 検知 |
| リソース枯渇型(Slowloris 等) | 接続タイムアウト、接続数制限 |
| 増幅攻撃(DNS/NTP) | 自分が踏み台にならない設定 |
「認証は OIDC で行い、アクセストークンは 10 分の JWT、 リフレッシュトークンはサーバー側で管理してローテーションします。 すべての API でリソースの所有者チェックを行い、URL の ID を信用しません。 サービス間通信は mTLS で相互認証し、DB の認証情報は Secret Manager から短命の動的認証情報として取得します。」
第 40 章 一問一答
- JWT の最大の弱点は。
- 即座に失効できないこと。短い有効期限とリフレッシュトークンで緩和する。
- パスワード保存に使うべきアルゴリズムは。
- bcrypt / scrypt / Argon2id(意図的に低速)。
- IDOR とは。
- リクエスト内の識別子を検証せず、他人のリソースにアクセスできてしまう認可の欠落。
- エンベロープ暗号化の利点は。
- マスター鍵の交換だけで鍵ローテーションでき、全データの再暗号化が不要。
CHAPTER 41プライバシーとコンプライアンス
個人データを扱う設計上の要件を説明できる。
41.1個人データの扱い
PII(個人識別情報): 氏名、メール、電話、住所、IP、Cookie ID、位置情報、
デバイス ID、生体情報
機微情報 : 人種、信条、健康、性的指向、犯罪歴 → より厳格な扱い
| 設計原則(Privacy by Design) | 実装 |
|---|---|
| データ最小化 | そもそも集めない。必要ないログは出さない |
| 目的限定 | 集めた目的以外に使わない(分析用途の同意は別) |
| 保持期間の制限 | TTL を設定し、自動削除する |
| 仮名化 / 匿名化 | ID を置き換える(仮名化は復元可能、匿名化は不可) |
| アクセス制御と監査 | 誰がいつ誰のデータを見たか記録する |
41.2GDPR / 各国法が要求する機能
| 権利 | 必要な機能 |
|---|---|
| アクセス権 | ユーザーの全データをエクスポートできる |
| 削除権(忘れられる権利) | 適用される例外、法定保存、法的請求、公共利益などを確認したうえで、対象システムから削除・不可視化・再利用停止できる |
| 訂正権 | 修正できる |
| データポータビリティ | 機械可読形式で提供 |
| 同意の撤回 | 追跡を停止できる |
法域ごとの例外と保存義務を確認し、削除要求の認証、期限、監査、第三者処理者への通知も設計します。
本体 DB → 削除・匿名化する レプリカ → 伝播する バックアップ → 保持期間中は変更せず、復元時に削除済み状態を再適用する設計もある ログ → PII を最小化し、保持期間・マスキングを適用 データレイク → 個人単位の削除・再生成・暗号鍵の分離を検討 イベントログ → 削除イベント、投影の再構築、暗号化消去を組み合わせる 検索インデックス、キャッシュ、CDN、第三者 SaaS → 削除伝播と監査を設計
ユーザーごとに個別の暗号鍵で PII を暗号化して保存する 削除要求 → その鍵を破棄する → その鍵で暗号化されたデータを復号できなくする。 ただし共有データ、メタデータ、バックアップ、鍵のコピー、法的要件を別途確認する。
暗号化消去を面接で言えると非常に強いです。実務的で、原理的な問題を解いているからです。
41.3データ分類とアクセス制御
Public : 公開情報 Internal : 社内限定 Confidential : 顧客データ(アクセスログ必須) Restricted : 決済情報、健康情報(暗号化 + 承認フロー + 監査)
本番データを開発環境にコピーしない。必要ならマスキング / 合成データを使う。
第 41 章 一問一答
- 削除権の実装が難しい理由は。
- バックアップ、ログ、分析基盤、イミュータブルなストアなど、データが多数の場所に複製されているため。
- 暗号化消去とは。
- ユーザー固有の鍵を破棄して復号不能にする手法。ただし例外、共有データ、バックアップ、鍵管理を別に評価する。
- 仮名化と匿名化の違いは。
- 仮名化は追加情報があれば復元可能、匿名化は復元不可能(法的扱いが異なる)。
CHAPTER 42コストの設計
設計判断にコストの観点を入れられる。
42.1コストの内訳(クラウドの相場感)
計算 (Compute) : 全体の 40〜60% ストレージ : 10〜20% データ転送 : 10〜30% ← 見落とされがち。特にリージョン間・インターネット向け マネージドサービス : DB、キュー、監視(意外と高い) 監視・ログ : ログの量に比例して爆発しがち
価格はクラウド事業者、リージョン、契約、ストレージ階層、時期で変わります。以下は固定値ではなく、見積もりの例として日付・リージョン・料金表の出典を併記して使います。
オブジェクトストレージ: 料金表から、保存容量・リクエスト・取り出しを分けて計算 インターネットへの外向き転送: 料金表から、データ量・宛先・無料枠を分けて計算 同一リージョン内の AZ 間転送: 料金表から、方向・サービス間転送を確認 CDN 経由の転送: CDN のリージョン、キャッシュヒット率、オリジン転送を含めて計算
保存費と配信費は別の料金体系で、配信が保存より高くなることがある。正確な倍率は料金表と実際の転送量で再計算する。CDN・キャッシュ・圧縮は性能施策であると同時にコスト施策です。
42.2コスト最適化の手段
| 手段 | 効果 | 注意 |
|---|---|---|
| 適切なインスタンスサイズ | 20〜50% | 定期的な見直しが必要 |
| リザーブド / Savings Plan | 30〜70% | コミットのリスク |
| スポットインスタンス | 60〜90% | 中断耐性のある設計が前提 |
| オートスケール | 20〜40% | 夜間・週末の縮小 |
| ストレージ階層 | 50〜80% | アクセスパターンの分析が必要 |
| ログの削減・サンプリング | しばしば劇的 | DEBUG ログの垂れ流しは高コスト |
| 圧縮 | 転送・保存とも | CPU とのトレードオフ |
| キャッシュヒット率の改善 | 全方位に効く | — |
| アーキテクチャの単純化 | 大きい | 部品が減れば運用費も減る |
42.3設計におけるコストの考え方
コストに言及すると、シニアなシグナルになります。
「動画のサムネイルを全解像度で事前生成すると、生成コストとストレージが膨らみます。 アクセス分布が上位コンテンツに偏るという仮説を、ログで検証します。 偏りが確認できるならオンデマンド生成 + CDN キャッシュにします。 生成回数、TTL、ヒット率、鮮度 SLO を測り、事前生成とのコストと体験を比較します。」
「1 リクエストあたりのコスト」「1 ユーザーあたりの月額コスト」を測ることで、機能追加の是非を定量的に議論できます。
月 $500 のコストを 30% 削るためにエンジニア 2 人が 1 ヶ月使うのは明確な損失です。大きい費目から順に見るのが鉄則です。
第 42 章 一問一答
- クラウドで見落とされがちなコストは。
- データ転送(特にインターネット向けとリージョン間)。
- CDN がコスト面で有利な理由は。
- オリジンからの直接転送より単価が安く、転送量そのものも減らせる。
- スポットインスタンスの前提条件は。
- 中断されても安全なステートレス・再実行可能なワークロードであること。
CHAPTER 43AI・機械学習・LLM・AI エージェントのシステム設計
大規模推薦システム、特徴量ストア、LLM 推論サービング基盤、RAG、AI エージェントの主要な構成とトレードオフを理解する。数値や性能はモデル、ハードウェア、ワークロードごとに実測する。
43.1なぜ「AI / ML のシステムデザイン」が特別なのか
従来の Web システム(CRUD)と機械学習システムには、根本的な 4 つの違いがあります。
| 観点 | 従来の Web システム | AI / ML・LLM システム |
|---|---|---|
| 計算特性 | I/O 律速(DB・ネットワーク待ち) | 計算律速 (GPU Compute) またはメモリ帯域律速 (VRAM Bandwidth) |
| データの性質 | 正確性(ACID・1 行の不整合も許さない) | 統計的・確率的(データの分布、鮮度、埋め込みベクトル) |
| パイプライン | 同期的なリクエスト/レスポンス | オフライン学習・リアルタイム推論・特徴量抽出の三重構造 |
| 障害モード | 500 エラー、タイムアウト | モデルの劣化(Data Drift / Concept Drift)、ハルシネーション |
モデルライフサイクルと評価
本番の ML は「モデルを学習してデプロイしたら終わり」ではありません。データとモデルの版を追跡し、同じ入力から同じ特徴量・予測を再現できるようにします。
データ収集・同意確認 → 品質検査(欠損、外れ値、ラベル漏洩、PII) → 学習・再現可能な実験 → モデルレジストリ(モデル、特徴量、データ、コード、評価の版) → オフライン評価 → シャドー / カナリア / A/B → 監視(品質、ドリフト、遅延、コスト、公平性、安全性) → 承認・ロールバック・再学習
オフラインの精度だけで本番品質を代表させず、オンラインのビジネス指標、ガードレール違反、セグメント別の性能、推論コストを分けて測ります。ラベルが遅い場合は代理指標と人手サンプルを併用し、データ削除・同意撤回・モデル更新が学習データと特徴量ストアへどう伝播するかも設計します。
43.2大規模推薦システム(Two-Tower モデルと 3 段階パイプライン)
Google YouTube、Instagram、TikTok などの推薦システムは、数億件のコンテンツから数十ミリ秒でパーソナライズされたフィードを生成します。これを 1 つの巨大なモデルで解くのは計算量的に不可能です。
10 億件の動画
│
▼ ① Candidate Generation (Retrieval / 候補抽出) [10〜20 ms]
数千件(1,000 件) ← Two-Tower Model + ANN (ScaNN / HNSW)
│
▼ ② Heavy Ranking (Scoring / 精密ランキング) [20〜30 ms]
数百件(100 件) ← 深層学習モデル (DLRM / Transformer) + 数千の特徴量
│
▼ ③ Re-ranking & Policy (ビジネスロジック・多様性) [5 ms]
数十件(20 件) ← 重複排除、探索と活用、鮮度ブースト、広告挿入
│
▼
ユーザーの画面へ
1. Candidate Generation(Two-Tower Model / Dual Encoder)
- ユーザー Tower:ユーザーの閲覧履歴、検索クエリ、年齢、時間帯などを入力し、ユーザー埋め込みベクトル u(D 次元)を出力
- アイテム Tower:動画のタイトル、タグ、カテゴリ、制作者情報を入力し、アイテム埋め込みベクトル v(D 次元)を出力
- 検索の仕組み:アイテムベクトルはオフラインで事前計算してベクターインデックス(ScaNN / HNSW)に格納。オンラインリクエスト時、ユーザー Tower だけをミリ秒で計算し、ANN 検索で内積 u・v の上位 1,000 件を 10 ms 以内に抽出
2. Heavy Ranking(精密ランキングモデル)
- 抽出された 1,000 件に対し、リッチな特徴量(「このユーザーがこの作者の動画を過去に最後まで見た確率」「過去 10 分間のクリック数」など)を結合
- 深層学習ランキングモデル(DLRM、Wide & Deep、Transformer など)で、CTR(クリック率)や視聴完了時間を予測
3. Re-ranking(多様性とビジネスルール)
- 同じ作者の動画が連続しないように分散(MMR: Maximal Marginal Relevance)
- 「探索と活用(Exploration vs Exploitation)」:新着動画を一定割合混ぜてユーザーの反応をテスト
43.3特徴量ストア(Feature Store)の設計
推薦や不正検知では、モデルに渡す「特徴量(Features)」の管理がシステムの成否を分けます。
┌─────────────────────────────────────────┐
│ Feature Store (Feast 等) │
├────────────────────┬────────────────────┤
│ オフラインストア │ オンラインストア │
│ (BigQuery / GCS) │ (Bigtable / Redis) │
└─────────┬──────────┴─────────┬──────────┘
│ │
学習時(バッチ) 推論時(リアルタイム)
・過去 1 年のログ ・直近 5 件の閲覧履歴
・Point-in-Time 一貫性・p99 < 5 ms の低遅延
- 「推論時に使っている特徴量計算ロジック」と「過去ログから学習用データセットを作るロジック」がずれると、モデルの精度が壊滅します
- 解決策:特徴量の定義コードを 1 つにまとめ、Feature Store がオフライン・オンライン両方に自動配信する
- Point-in-Time Correctness(タイムトラベル):過去のイベント時点での正確な特徴量を復元し、未来のデータが学習に混入する「データリーク」を防ぐ
43.4LLM 推論サービング基盤の基礎
ChatGPT や Gemini のような大規模言語モデル(LLM)の推論は、通常の Web サーバーとは全く異なるリソース制約を持ちます。
① Prefill(プロンプト処理)vs Decode(トークン生成)
| フェーズ | やること | ボトルネック | 性質 |
|---|---|---|---|
| Prefill | 入力プロンプト(例:1000 トークン)を一度に処理 | Compute-bound(GPU 計算律速) | 並列化が効く。TTFT(最初の 1 トークンが出るまでの時間)を支配 |
| Decode | 1 トークンずつ自己回帰的に生成 | Memory Bandwidth-bound(VRAM 帯域律速) | 1 系列の時間方向は逐次だが、系列間バッチング、テンソル並列、投機的デコードなどの並列化は可能 |
② KV Cache と PagedAttention(最重要)
Transformer は過去の全トークンの Key と Value の行列(KV Cache)を保持して計算をスキップします。
KV bytes = 2 × layers × KV heads × head dim × sequence length
× batch size × bytes per element
- 先頭の 2 は K と V の 2 種類です。MHA では
KV heads × head dim = hidden sizeになりますが、GQA/MQA では KV ヘッド数が小さいため、隠れ層サイズだけで計算してはいけません - 例:80 層、GQA の 8 KV ヘッド、head dim 128、4K トークン、FP16 なら、1 リクエストは約 1.34 GB(10 進)です。MHA で 8192 次元なら約 10.7 GB です
- 実際の同時実行数は、モデル重み、ランタイム、ワークスペース、断片化、バッチングの余裕を引いて実測します
- 従来は「最大コンテキスト長(例:8K)」分の連続メモリを事前に確保していたため、実際の長さの分布によってはメモリ利用率が大きく落ち、無駄な OOM が発生する
- PagedAttention(OS の仮想メモリページングと同じ思想):KV Cache を固定サイズ(例:16 トークン)の「ブロック(ページ)」に分割し、物理 VRAM の不連続な領域に動的割り当て。メモリ利用率と同時処理数の改善幅は、実装、ベースライン、モデル、ワークロードで測定する
③ Continuous Batching(動的・インフライトバッチング)
- 静的バッチングの課題:10 人のリクエストをまとめた場合、一番長い出力(1000 トークン)が終わるまで、短い出力(10 トークン)の人も GPU を拘束し続ける
- Continuous Batching:1 トークン生成するイテレーションごとに、生成が完了したリクエストを即座に排出し、キューにある新しいリクエストを動的にバッチへ差し込む。スループットの向上幅は、出力長、バッチサイズ、スケジューラ、モデル、SLO を同じ条件で測定する
④ 投機的デコーディング(Speculative Decoding)
軽量なドラフトモデル(7B)が高速に 4〜5 トークンを先読み生成し、巨大なターゲットモデル(70B)が 1 回のフォワードパスで検証する。速度向上は受理率、モデル、負荷に依存する。
43.5RAG(検索拡張生成)の完全アーキテクチャ
LLM に最新情報や社内ドキュメントを参照させる標準パターンです。
[ユーザーの質問]
│
▼
[① Query Rewriting / HyDE](質問を検索しやすい形・仮想回答に変換)
│
▼
[② ハイブリッド検索] ──┬──► [BM25 転置インデックス]
└──► [Embedding モデル] → [ベクター DB (HNSW)]
│
▼
[③ RRF 統合](上位 50 件を抽出)
│
▼
[④ Cross-Encoder リランカー](上位 5 件に高精度に絞り込み)
│
▼
[⑤ コンテキスト圧縮 & プロンプト構築]
│
▼
[⑥ LLM 推論サービング] ──(ストリーミング SSE)──► [クライアント]
セマンティックキャッシュ(Semantic Cache)
- プロンプトの完全一致(MD5)ではなく、Embedding の類似度で候補を探す方式。ただし、類似度の閾値はデータで検証する
- キャッシュキーにはテナント、ユーザー権限、モデル版、システムプロンプト、ツール、データ鮮度を含める。個人情報・高リスク回答を無条件に共有せず、コストとレイテンシの改善幅は実測する
43.6AI エージェントの本番システム設計
AI エージェントは「LLM に長いプロンプトを渡すこと」ではありません。モデルが計画を立て、ツールを呼び、結果を解釈し、状態を更新して次の行動を選ぶ制御ループです。手順が固定されているなら、自由なエージェントより通常のワークフローやステートマシンの方が安く、再現性が高く、検証しやすい、という判断から始めます。
① 基本ループと責任の分離
[要求 + ユーザー/テナント境界]
│
▼
[ポリシー・能力チェック] ── 許可されたツールだけを公開
│
▼
[計画 / ルータ] ──► [ツール実行(サンドボックス、期限、予算)]
│ │
│ ▼
│ [結果の検証・副作用の確認]
│ │
└──── [状態・監査ログへチェックポイント] ◄─┘
│
継続 / ユーザー確認 / 完了 / 停止
モデルには「何を考えたか」ではなく、必要な構造化出力(ツール名、引数、根拠、次の状態)を返させます。認証・認可、予算、リトライ、監査、外部副作用の確定は、モデルの判断に任せず決定的な実行器で担保します。
② ツール契約(Agent–Computer Interface)
ツールは関数呼び出しの名前だけでは不十分です。各ツールに次の契約を持たせます。
| 契約 | 設計すること |
|---|---|
| 入出力 | 型付きスキーマ、単位、必須・任意、許容範囲、エラー形式 |
| 副作用 | read-only / 可逆変更 / 不可逆変更を分類し、dry-run を用意 |
| 信頼性 | タイムアウト、キャンセル、冪等キー、重複検知、状態照会 API |
| 権限 | ユーザー・テナント・リソース単位の最小権限。ツールごとに許可範囲を制限 |
| 安全性 | URL、SQL、シェル、ファイル、プロンプトを無害化。ツール結果も untrusted input として扱う |
| 監査 | 呼び出し元、モデル版、引数のハッシュ、結果、承認者、相関 ID を記録 |
「タイムアウトしたので再実行」は、外部で既に処理されたか分からない非原子的失敗を起こします。冪等キーで重複を抑え、再試行前に状態照会または事後条件(残高が減った、チケットが発行された等)を検証します。支払い、削除、送信、権限変更など不可逆操作は、明示的な確認・人間承認・二重チェックを要求します。
③ 状態、メモリ、長時間実行
「コンテキストに履歴を全部詰める」設計は、トークン費用・漏洩・コンテキスト上限で破綻します。少なくとも次を分離します。
- 作業コンテキスト:現在のターンで必要な短期情報。要約・圧縮・期限を持つ
- タスク状態:ステートマシン、実行 ID、試行回数、期限、チェックポイント、未完了ツールを永続化する
- 知識・長期メモリ:出典、テナント、権限、鮮度、削除状態、モデル版を付けた検索可能なデータ
ワーカーが落ちてもチェックポイントから再開できるようにし、同じステップを再実行しても結果が壊れないようにします。最大ステップ数、最大トークン、経過時間、外部 API の費用、並列数を上限にし、上限到達時は安全に停止してユーザーへ引き継ぎます。
④ セキュリティとプロンプトインジェクション
取得文書、メール、Web ページ、ツール応答に含まれる「指示」は、システムポリシーより下位のデータです。それらを命令として実行すると、秘密情報の持ち出し、越権操作、SSRF、データ汚染につながります。
- システム指示、ユーザー入力、取得データ、ツール結果を構造的に分離する
- ツールを能力(capability)単位で分け、不要な秘密・ネットワーク・ファイルにアクセスさせない
- 外部 URL は許可リスト、DNS 再解決、プライベート IP・メタデータサービス遮断を行う
- 出力だけでなく、引数・権限・副作用を決定的なポリシーエンジンで検査する
- テナント境界、削除、監査、保持期限を RAG・キャッシュ・メモリ・ログにも適用する
⑤ 評価・観測・運用
最終回答の正しさだけでなく、軌跡(trajectory)を評価します。代表的な指標は、タスク成功率、正しいツール選択・引数率、不要な呼び出し率、再試行・停止の適切さ、制約・ACL 違反率、人間への引き継ぎ率、p95/p99 レイテンシ、トークン・ツール費用です。
固定のゴールデンケース、過去トレースのリプレイ、敵対的入力、権限境界、長時間・部分障害を組み合わせます。LLM-as-a-judge は補助に留め、人手サンプルや決定的な検査(スキーマ、ACL、状態遷移、事後条件)で校正します。本番では、モデル版・プロンプト版・ツール版・入力要約・各呼び出し・判断結果を Trace ID で結び、カナリア、キルスイッチ、予算アラート、ロールバックを用意します。
⑥ 単一エージェント、ワークフロー、マルチエージェント
| 方式 | 向く状況 | 主なリスク |
|---|---|---|
| 決定的ワークフロー | 手順・分岐・SLO が明確 | 例外が増えると分岐の保守が難しい |
| 単一エージェント | ツール数が少なく、探索や計画が必要 | ループ、権限過剰、費用の予測困難 |
| マルチエージェント | 独立した専門タスクを並列化し、契約で結果を渡せる | 通信・調停・重複作業・障害の増幅。最初から採用しない |
マルチエージェントにする場合も、各役割の入力・出力スキーマ、タイムアウト、予算、再試行、停止条件、責任者を定義します。共有の自由文メモだけで協調させず、中央のオーケストレータが権限と状態遷移を管理します。
「まず固定手順ならワークフローにします。探索が必要な部分だけエージェントにし、 ツールは read-only と副作用ありに分けます。 各呼び出しに期限・冪等キー・最小権限・事後条件を持たせ、 タイムアウト時は状態照会してから再試行します。 実行状態をチェックポイント保存し、ステップ数・費用・時間の上限で停止します。 削除や決済は人間承認、全文書とツール結果は untrusted input、 監査トレースとリプレイ評価でモデル更新をカナリアします。」
第 43 章 一問一答
- 推薦システムで Two-Tower モデルを使う最大の理由は。
- アイテム埋め込みをオフライン事前計算し、オンラインではユーザー埋め込みと ANN 検索だけで数ミリ秒で数億件から候補を絞り込めるから。
- LLM の Decode フェーズがメモリ帯域律速になる理由は。
- 1 トークン生成するごとにモデルの全パラメータと KV Cache を VRAM から読み出す必要があり、GPU コアの計算能力ではなくメモリ転送速度が限界を決めるため。
- PagedAttention の効果は。
- KV Cache を不連続なブロックで管理して内部断片化を減らす。利用率や同時処理数の改善幅は実装とワークロードで評価する。
- Continuous Batching とは。
- トークン生成の 1 ステップごとに完了したリクエストを排出し、新規リクエストを動的にバッチに追加する手法。
- 固定手順をエージェントにしない理由は。
- 決定的ワークフローの方が再現性、費用、検証可能性を確保しやすく、自由な探索が必要な部分だけをエージェントにできるから。
- ツール呼び出しがタイムアウトしたら即再試行してよいか。
- いいえ。外部で実行済みかを状態照会または事後条件で確認し、冪等キーと予算の範囲で再試行する。
- AI エージェントの評価で最終回答以外に見るものは。
- ツール選択・引数、状態遷移、制約・ACL 違反、不要な呼び出し、停止・引き継ぎ、遅延と費用を軌跡単位で測る。
- プロンプトインジェクションへの基本姿勢は。
- 取得文書やツール結果を命令ではなく untrusted input として扱い、能力・権限・副作用を決定的な層で制限する。


