「善意」が「負債」に変わる瞬間 —— レガシー改修で“誰も幸せにならない結末”を避けるための生存戦略
「やってしまった」という痛恨の経験から
先日、ある案件で久しぶりに「やってしまった」という痛恨の経験をしました。
対象は10年以上前に開発された、いわゆる「レガシー」なシステム。当時の担当者は誰も残っておらず、設計書はもはや古文書。一度は「リスクが高すぎる」と受注を辞退したものの、長年の付き合いや顧客側の予算・納期といった「大人の事情」に押し切られる形で、私はそのコードにメスを入れることを決意しました。
「多少のリスクは織り込み済みだ」——そう自負していましたが、現実は甘くありませんでした。
コア機能の一角を動かした瞬間、まるでジェンガが崩れるように、関係ないはずの機能が次々と悲鳴を上げ始めたのです。予期せぬ再構築、雪だるま式に増える修正、そして受入テストで放たれる「業務に支障が出るから直して」という、要件定義を無効化する魔法の言葉。
結局、寝る間を惜しんでコードを書き換えたものの、残ったのは疲弊したチーム、パッチだらけの仕様、そして「高い金を払ったのに」という顧客の不満。誰も幸せにならない結末でした。
なぜ、エンジニアとしての誠実な対応が、最悪の結果を招いてしまったのか。この苦い教訓を、単なる「失敗談」で終わらせないために。技術力以前に私たちが身に着けておくべき「防波堤の築き方」を整理しました。
1. はじめに:なぜ「正論」は現場で通じないのか
「要件定義書にないものは対象外です」。
見積もり時に何度繰り返したところで、実際の画面を触った顧客から「これじゃ仕事にならない」と言われれば、現場のエンジニアは折れざるを得なくなります。
本記事では、10年もののレガシーシステムをベースにしたカスタマイズ案件で、なぜ 「正しい見積もり」と「誠実な対応」が、最悪の結果(品質低下・信頼失墜・チームの疲弊)を招いてしまう のか、その構造的な問題と対策を考察します。
2. 破綻へのシナリオ:誠実さが仇となる「負のループ」
今回の失敗は、個別の技術力不足ではなく、以下のような「構造的な罠」によって進行しました。
- 【受注の罠】:環境の古さを理由に一度は断るが、顧客側の予算・納期固定という外圧に押し切られ「毒饅頭」を食べてしまう。
- 【不確実性の爆発】:10年前の設計は想像を絶する密結合。影響範囲の見極めは、稼働中のコードを剥がしてみるまで不可能だった。
- 【受入テストのどんでん返し】:合意したはずの要件が「業務に支障が出る」という最強のカードで上書きされる。
- 【なし崩しの対応】:断ればプロジェクトが止まるため、短期間で無理なコード変更を強行。
- 【破綻】:仕様が不整合を起こし、品質が低下。顧客は「金と時間をかけたのにボロボロだ」と不信感を募らせ、開発者は心身ともに削られる。
3. エンジニアが設計・実装以外に身につけるべき「生存スキル」
設計やコーディングが完璧でも、以下の「非技術的スキル」が欠けるとプロジェクトは沈みます。
① 「幅」を持たせた合意形成(コーン・オブ・アンサーティンティ)
レガシー改修において、一点張りの見積もりはギャンブルです。
- 「調査が終わるまでは、工数に±50%の変動がある」
- 「コア機能に手を入れる場合、波及範囲次第で納期を再調整する」
という、不確実性を前提とした契約・合意を握るスキルが不可欠です。
② 「NO」の代わりとなる「トレードオフ」の提示
「できません」は拒絶ですが、「やるなら、代わりにこれを捨てましょう」は交渉です。
「業務に支障が出るから追加してくれ」と言われた際、「了解しました。では、品質担保のために納期を延ばすか、予定していた機能Bを次フェーズに回しましょう」と、リソースの等価交換をその場で突きつける勇気が必要です。
4. 体制による解決:一人で抱え込まないための防衛線
今回、打診から見積もり、実装フェーズまで同じ人間が一貫して行ったことが最大のボトルネックでした。これを防ぐための「体制」による改善案です。
案1:営業・PMとエンジニアの役割分離
エンジニアが直接交渉すると「技術的に可能か」で判断してしまいがちです。
- PM(プロジェクトマネージャー)を立てる:顧客の「業務上の困りごと」を受け止めつつ、契約のガードレールを守る役割。エンジニアが「作らされる側」ではなく「技術的助言をする側」に回ることで、冷静な判断が可能になります。
案2:有償の「事前調査フェーズ」の徹底
見積もり前に、コードを解析し、プロトタイプを作る期間を独立した案件として受注します。
- 「開けてみないと分からない」を「開けてみた結果、これだけのリスクがあった」という事実(エビデンス)に変えてから、本契約に進みます。
案3:第三者によるリスクアセスメント
一人で担当すると、「自分が頑張ればなんとかなる」という生存バイアスがかかります。
- 見積もり段階で、別のエンジニアが「このレガシーコードに対してこの納期は無謀」と客観的なアラートを鳴らす仕組みを作ります。
5. おわりに
「お客様のために」となし崩しに対応することは、短期的には親切に見えますが、最終的に壊れたシステムを納品することになれば、それは最大の不誠実になってしまいます。
エンジニアとしての誠実さとは、無理なものに「無理」と言い、品質と設計を守るための戦いを避けないことにある。
今回の痛恨の経験を、次なる堅牢なプロジェクト運営の糧にしていきましょう。