コンテンツにスキップ

全てのことに意味がある

全てのことに意味がある

1on1 やチームメンバーとの会話で、よく伝えていることがある。 「全てのことに意味がある」という話だ。

これは私自身の経験から来ている。

社会人歴は 2026 年 1 月時点で 7 年目になる。 1 社目を約 4 年間勤めて、現職について 3 年目だ。

1 社目の自分は、ずっとプログラミングをすることが自分にとっての幸せであり、そこだけを極めることに意味があると思っていた。 デザインパターン、クリーンアーキテクチャ、様々な言語の仕様。 そのために営業部や技術部といった区分けがあるのだろうとも思っていたし、自分は技術の世界だけで生きていくのだと信じていた。

1 社目を辞めた理由は、「やれることが少なくなった」からだ。 当時の業務は、15 年以上稼働を続けるシステムの保守開発だった。 VB.NET を使い、画面とロジックが密結合になっている。言語やフレームワークの制約上、完全な疎結合にすることは難しかった。

その中でも、新規機能についてはテスタビリティを向上させる動きをしたし、精一杯やったと思う。 でも当時の私は「ソフトウェアアーキテクチャを 1 から学びたい」という気持ちが強くなり、新しい環境を求めて転職した。

今振り返ると、それは狭い視野が原因だった。 本気で学びたかったなら、そのシステムをより良くするためにもっと動いていくべきだったのかもしれない。 「もっと新しい世界を見たい」というのは、当時の自分を心地の良い場所へ向かわせるための言い訳だったのかもしれない。

でも、逃げだったとしても、逃げた先で得たものは多くある。 今の環境では、前の会社で 10 年以上働いた後に任されるような仕事に携わっている。 あの時「正しい選択だ」と信じて飛び出した自分を、今は否定しない。

現職では、プリセールス活動をしている。 営業と一緒に顧客に対して、自社での案件獲得に向けて動く活動だ。

お客様の課題を把握して、「自社の技術でこういったことができますよ」という提案を行い、それが刺されば発注していただける。 でも、そのプリセールス活動というのは、どれだけプログラミングの技術が優れていたとしても、それだけでは歯が立たない。

とあるプリセールスで、私は DevOps の導入を提案した。 開発リソースが足りないという技術部署のリーダー層が相手だった。 Netflix や Amazon で開発生産性が向上した事例を紹介しながら、自信を持って説明した。

でも、相手の反応は冷たかった。 「うちはそんな大企業じゃないから、こんなの無理でしょう」 本当はその後、その企業向けにカスタマイズした内容を説明するつもりだった。でも、「もういい」と途中で打ち切られてしまった。

自分では相手に寄り添った提案だと思っていた。 でも、相手にとっては「自分の会社でできるイメージが湧かない」話だった。 「寄り添えていなかった」というのは、こういうことなのかと思い知らされた。

お客様(決裁権を持っている人)が完全に技術者であれば技術の話は刺さる。 でも、そうでないことの方が多い。 経理部署、人事部署、IT とは関係のないビジネスサイドの人たち。 当たり前だが、お客様の抱える課題は技術視点ではなくビジネス視点になる。

そこに対して、「クリーンアーキテクチャが〜」とか「言語仕様が〜」みたいな話をしても響かない。 最終的には How として技術を活用するが、まずは What を理解しなければいけない。 抽象度を上げて課題を聞き、ビジネスを変えるための提案をする。

そういった「具体と抽象の行き来」が、あとから振り返った時に、自身のエンジニアリング活動に強く紐づいていることに気づいた。

1on1 で時間が余った時や、これから花を咲かせる若手と一緒に資料作成をする時、私はこんなことを話す。

「資料作成で気にしていることがあるんだけど、行間や色使い、ページを俯瞰した時の情報整理ってすごく大事で。 口頭がメインで補足としての資料なのに、文字が詰まっていたら伝わらないよね。 箇条書きにする時は MECE になっているかなって気にするんだけど、それってコード設計と同じ構造なんだよね。」

ソフトウェアエンジニアリングでモジュールを分割する時も同じだ。 冗長なクラスを分けたり、共通のロジックを共通化したり。 「どう整理すれば伝わりやすいか」という視点は、資料でもコードでも変わらない。

コーディングエージェントとデフォルト引数

Section titled “コーディングエージェントとデフォルト引数”

1on1 で SRE のメンバーからよく聞く話がある。 Terraform のコードをコーディングエージェントと一緒に実装していると、デフォルト引数を入れがちだという話だ。

前職で病院関連のシステム開発をしていたので、その経験を元に少し例を変えて紹介する。

// Before: 2つのサービスで似たような処理がある
class HospitalService {
async sendNotification(patientId: string, message: string) {
// 100の病院で稼働中のロジック
}
}
class ClinicService {
async sendNotification(patientId: string, message: string, priority: string) {
// 新規開発中のロジック
}
}

コーディングエージェントにリファクタリングを依頼すると、こうなりがちだ。

// After: エージェントがデフォルト引数で「安全に」共通化
class NotificationService {
async sendNotification(
patientId: string,
message: string,
priority: string = "normal" // 既存に影響を与えないためのデフォルト
) {
// 共通化されたロジック
}
}

エラーにはならない。でも、保守性が悪い。

システムにはコンテキストに含められていない背景がある。 100 の病院で動いているロジックなら人の命に関わる。そのロジックには一切手を入れないようにデフォルトを入れる、という判断はありえる。

しかし、これから開発するシステムは違う。 リリース前でシステムデザインを構築する段階なら、呼び出し側が意図を持って値を指定した方がいい場合が多い。

インフラでも同じことが言える。Terraform で dev/prod それぞれから呼ぶモジュールがある時、モジュール側の default 値に頼り切って、dev/prod から値を入れない。dev/prod のリソース定義のために書いているのに、module の default 側に隠蔽されてしまう。

背景(ビジネス的なのか、技術的なのか)を把握し、検討した上で定義していく必要がある。 そして、そういったものたちには理由を持っていなければならない。


プリセールスで学んだこと、資料作成で気にしていること、コード設計で考えていること。 それぞれ別の話のようで、どれも「具体と抽象の行き来」という同じ構造を持っている。

1 社目では「具体」だけを見ていた。 だから「やれることが少なくなった」と感じた。 でも本当は、その具体を通じて抽象を学ぶ機会はあったはずだった。

今の組織構造に不満を持つこともある。 でも、その中でやることなすこと全てに意味があると信じてやっている。

だから私は、1on1 やチームメンバーとの会話で、こう伝えている。 「一見関係ないことでも、いつか繋がる時がくる」と。

もちろん私もまだまだ勉強中だ。 でも、感じたことは新鮮なうちに言葉にした方がいいと思っている。