層を分ける理由は「なぜ工程として必要なのか」で述べた。 だが実際の文書では、層は宣言だけでは守られない。書いているうちに静かに越境する。
越境には方向がある。下向き(上位層の文書に下位層の判断が先回りして書かれる)と、 上向き(下位層で発生した都合が、検証されないまま上位層の決定として居座る)である。 方向によって症状も直し方も違うため、分けて扱う。
判定の基準はひとつ。その記述を「正しい」と言える人が、その文書の検証者と一致しているか。 一致していなければ越境している。
以下の例は、業種・システム種別を意図的に散らしてある。 越境は特定のドメインの癖ではなく、層を扱うかぎりどこでも起きるためである。
もっとも頻度が高く、もっとも損失が大きい。
| 症状 | 要求定義書の目的欄に、作るものの名前が書いてある |
| 例(EC) | ✗「レコメンドエンジンを導入する」 ✓「カゴ落ち率を32%から20%に下げる」 |
| 例(社内) | ✗「勤怠管理システムを刷新する」 ✓「月次締めの差し戻しを月40件から5件以下にする」 |
| 失われるもの | 代替案の検討余地。カゴ落ちは送料表示のタイミング変更で解ける可能性があるが、レコメンドと書いた時点で検討対象から外れる |
| 直し方 | 「それができると何が嬉しいのか」を3回問う。システムの話でなくなったところが要求 |
解決策が要求の位置に座ると、以降の全層がその解決策を前提に積み上がる。 要求が間違っていたと分かるのは運用に入ってからで、そのときには修正コストが桁で変わっている。
| 症状 | 「業務を効率化する」「顧客満足度を向上させる」で止まっている |
| 例(サポート) | ✗「問い合わせ対応を改善する」 ✓「一次回答までの中央値を8時間から2時間にする」 |
| 失われるもの | 受入テストの根拠。発注者が「それが欲しかったものか」を判定できない |
| 直し方 | 数値と期限を入れる。入れられないなら、まだ要求が言語化されていない |
V字モデルで要求に対応するのは受入テストである。 検証者が正誤を言えない要求は、対応する検証が空になる。
| 症状 | 実現手段が要件として合意されている |
| 例(Webサービス) | ✗「Redisでセッションを管理できること」 ✓「複数サーバー構成でもログイン状態が維持されること」 |
| 例(モバイル) | ✗「Firebase Cloud Messagingで通知を配信すること」 ✓「在庫が復活した商品を、登録者に30分以内に通知できること」 |
| 失われるもの | 設計の自由度。要件として合意した以上、後から別の手段に変えるのが契約上の変更になる |
| 見分け方 | 製品名・ミドルウェア名・アーキテクチャ名が出てきたら設計層 |
| 症状 | 要件定義書に画面レイアウトやボタン配置が書かれている |
| 例(予約サービス) | 要件は「予約の変更が予約者本人でできること」。 「マイページ内に変更ボタンを置く」は仕様の話 |
| なぜ起きる | 発注者に説明するとき、画面があるほうが伝わるため |
| 問題 | 説明のための画像が、いつのまにか合意事項として扱われる |
| 直し方 | 画面を出すなら「これはイメージであり仕様ではない」と明記する。合意対象は文章側 |
| 症状 | 発注者に説明する内容と、実装者向けの補足が同じ節に同居している |
| 問題 | 発注者は読めない箇所を読み飛ばし、実装者は合意済みと未確定の区別を失う |
| 直し方 | 章または節の単位で分離し、どちらが合意対象かを明示する |
同じ文書に2種類の読者がいるとき、層の境界より先に読者の境界が壊れる。
| 症状 | 「適切に処理する」「必要に応じて考慮する」「十分な性能を確保する」 |
| 例(社内文書) | ✗「承認者が不在のときは適切に処理する」 ✓「承認待ちが3営業日を超えたら代理承認者へ自動転送する。代理承認者が未設定の場合は申請者の部門長に通知し、申請は差し戻さない」 |
| 問題 | 仕様の検証者はテスター・レビュアーである。正誤を判定できない記述は、仕様の役割を果たしていない |
| 直し方 | 「これをどう試験するか」を書いてみる。書けないなら決まっていない |
| 症状 | 入力と出力は書かれているが、上限・0件・エラー・同時実行が書かれていない |
| 例(予約) | 「空き枠を選んで予約できる」だけが書かれ、最後の1枠を2人が同時に押した場合が書かれていない |
| 例(社内文書) | 同じ規程を2人が同時に編集して保存した場合の扱いが未定義。後勝ちか、警告を出すか、版を分けるかが決まっていない |
| 何が起きるか | 実装者が実装中に決める。決めた事実がどこにも残らない |
| 直し方 | 入力・出力・条件・例外の4点セットを埋めきるまで仕様としない |
未定義の例外系は消えるのではなく、コードの中に無記名で確定する。
| 症状 | クラス名とメソッド名の一覧はあるが、なぜその構造にしたかがない |
| 書くべきこと | 「注文と在庫引当を同一トランザクションにせず、非同期にした。理由はピーク時のロック競合を避けるため。採らなかった案は同期+悲観ロックで、整合性は単純になるが秒間注文数の上限が読めなかった」 |
| 問題 | コードを読めば分かることしか書いておらず、コードから読み取れない判断が残っていない |
| 直し方 | 検討して採らなかった案とその理由を書く。設計書の価値はそこにある |
下向きは書き手の先走りだが、上向きは追認である。 起きてしまったことを事後的に正当化するため、指摘されにくく、発見が遅れる。
| 症状 | 実装中に判明した制約が、そのまま仕様書に反映される |
| 例(外部連携) | 配送会社のAPIが1分1回までだったため、追跡情報の更新間隔を1分にした。それが「仕様」として書かれ、なぜその値かは残らない |
| なぜ問題か | 上の層へ差し戻さず、コードで解決してしまっている |
| 正しい手順 | 仕様の検証者(レビュアー)に判断を戻す。その上で仕様を変えるなら、変更として記録する |
結果として同じ仕様に落ち着くこともある。問題は結論ではなく、誰が決めたかが残らないことにある。
| 症状 | 下位層の妥協が積み重なり、要求の成功基準が未達になっているが、誰も気づかない |
| 例(社内文書) | 全文検索のインデックス更新が重いため、反映までを「1時間以内」に緩めた。要求にあった「承認された規程を関係者がすぐ参照できる」は成立しなくなっているが、仕様書上は整合している |
| なぜ起きる | 仕様の変更として処理されるため、要求層まで影響が伝わらない |
| 直し方 | 仕様を変えるとき、上位の成功基準に触れるかを必ず確認する |
これは越境の中でもっとも静かで、もっとも危険な種類である。 文書上はすべて整合しているのに、要求が達成できない状態が完成する。
| 症状 | 「不具合対応」として振る舞いが変わっている。仕様書は更新されていない |
| 例(社内文書) | 規程の改定時に、旧版へのリンクが自動的に新版を指すよう変更した。仕様書に版の参照方法の記載がなかったため「バグ」として処理されたが、実際には「当時どの版を参照していたか」を監査時に追えなくする仕様変更 |
| 問題 | 仕様書と実態がズレる。次に仕様書を信じた人が誤る |
| 見分け方 | 「決めたとおりでない」がバグ、「決めたことが間違っていた」は仕様変更 |
逆方向(仕様変更をバグ修正と主張する)は、受託では費用負担の争点に直結する。 層の区別がそのまま契約の区別になる場面である。
| 症状 | どんな要望も「ではコードをこう直します」から会話が始まる |
| 例 | 「もっと使いやすくして」に対し、ボタンの色と配置の調整を繰り返す。要求層で「誰がどこで詰まっているか」を確かめていないため、何度直しても評価が変わらない |
| 直し方 | 受けた時点で「これは要求/要件/仕様/設計のどれの変更か」を先に言語化する |
層を分けた本来の効能は、変更時の影響範囲の特定にある。 これが失われると、層は文書の飾りになる。
| 症状 | 1つの文書に背景・機能一覧・画面・テーブル定義が同居している |
| 問題 | 検証者が特定できない。誰もレビューを完了できず、承認だけが形式的に行われる |
| 直し方 | 分割の基準は分量ではなく検証者。読む人が変わるところで切る |
| 症状 | 仕様書と設計書は最新だが、要件定義書が初版のまま |
| 例 | 途中で対象ユーザーが「店舗スタッフのみ」から「本部を含む」に広がったのに、要件定義書は店舗前提のまま。権限設計の議論が毎回ふりだしに戻る |
| なぜ起きる | 日々参照するのは下の層だけで、上の層は「合意済みの過去」として凍結される |
| 直し方 | 上位層は変更頻度が低いだけで、変わらないわけではない。変えたら書く |
| 症状 | 同じ対象が層ごとに違う名前で呼ばれている |
| 例(EC) | 要求では「お客様」、要件では「会員」、仕様では「ユーザー」、設計では customer。未登録の購入者を含むのかどうかが誰にも分からない |
| 問題 | 同じものか別のものかが読み手に判断できず、追跡が切れる |
| 直し方 | 用語集を要求層に置き、下位層はそれを参照する |
文書を書き終えたら、次を順に確認する。
いずれも「なぜ工程として必要なのか」で挙げた問いの言い換えである。 この判断は誰が検証するのか。答えられない記述が、越境した記述である。