技術的負債に真剣に向き合ってみる

# TL;DR
- [この世界は解決を待っている魅力的な問題でいっぱい](http://cruel.org/freeware/hacker.html)
- 名付けて満足しない
- 本当に解決すべき問題を分類し共有する
- 解決して得られるものがなければ、泣く泣く放置する

---

# この文章の目的
技術的負債という言葉で曖昧になってしまい、本当の問題が隠されることがある。
そのような状況を打破し、本当に取り組むべき課題を明らかにして、具体的な活動へつなげていくためのガイドラインとなるべき共通認識を、エンジニア・非エンジニアに関わらず持っていきたい。

---

# 技術的負債とは何か

[Wikipedia(英語)](https://en.wikipedia.org/wiki/Technical_debt)
[Wikipedia(日本語)](https://ja.wikipedia.org/wiki/%E6%8A%80%E8%A1%93%E7%9A%84%E8%B2%A0%E5%82%B5)
明確な定義はない。

[「技術的負債」とは何か。原典とその対応策を探る](http://www.publickey1.jp/blog/13/post_232.html)という記事が面白いが、やはり技術的負債を明確に定義する記事は見つからず。

---

## なぜ定義が必要か

- 経験と勘で技術的負債か否かを判断してはならない
- 技術的負債とラベリングすると、何でも解決しなければならなく見える
- 負のイメージの名前をつけて悦に浸るのかっこ悪い（反省）

---

# 技術的負債の分類
なので、あくまで自分の経験を元にではあるが、基準を作って考えてみることにする。

---
## 考える軸

| 考慮すべき点 | 何を考えるか |
|---|---|
|レイヤー|システムに関わるどのレイヤーで負債が発生するか|
|観点|なぜ負債と捉えられるか|
|影響|負債を残すと何が消費されるか|

---

### レイヤー

- 構成
- ミドルウェア
- 利用技術（html5とかのパラダイム的なもの）
- 言語
- フレームワーク
- コード
- 人

---

### 観点

- 変更容易性
- 安定性
- スケーラビリティ
- 運用費用

---

### 影響

- 事業継続性（BC）に関わるもの
- 事業の柔軟な変化に関わるもの
- エンジニアのスキルに制限が加わるもの
- エンジニアの定着に関わるもの

---

観点と影響は同じようなものと捉えられるが、非エンジニアに説明する際には影響を説明することでスムーズになると考えられる。
例えば、スケーラビリティの貧弱なシステムの影響はBCPが脆弱になる他、スケーラブルでないシステムに比べてエンジニアに対して高スキルを要求することになる。

言い換えれば、影響のどこかを諦める（耐えしのぐ）ことができるのであれば、自転車操業可能な負債であるといえる。

---

## 典型的な例

---

### 保守性の低いコード

- 長いメソッド
- 複雑なSQL
- テストのないメソッド
- 謎のマジックナンバー
- いびつなクラス設計
- 俺俺フレームワーク

---

| 分類 | 分類先 | なぜ |
|---|----|----|
|レイヤー|利用技術・フレームワーク・コード| - |
|観点|変更容易性・安定性|不要なパズルを解く必要があるコードは悪|
|影響|柔軟な変化・スキル・定着|変化したいのであれば、超人的に特化したエンジニアが定着すること|

---

#### 対処方法
- 返済：リファクタリング、新技術・フレームワークの導入（新しいものは基本的に効率化されている）
- 自転車操業：ノウハウの伝授、定着のための高待遇

---

### 脆弱なシステム構成
- SPOF（単一障害点）の多い構成
- アップデートされていないミドルウェア
- 管理されていない公開サーバ
- 後からつぎはぎされた関連システム

---

| 分類 | 分類先 | なぜ |
|---|----|----|
|レイヤー|構成・ミドルウェア| - |
|観点|安定性・スケーラビリティ・運用費用|つぎはぎで作られたシステムは無駄な構成があって運用費に跳ね返ることもある|
|影響|BC・スキル|脆弱なシステムでは、エンジニアが注意しなければ問題が発生する|

---

#### 対処方法
- 返済：構成変更、APIの分離
- 自転車操業：モニタリングの強化、24H対応の人材

---

### プロフェッショナル意識の欠如
- コピペコード
- 適切なコード規約がない
- バージョン管理のないコード
- その場しのぎの運用

---

| 分類 | 分類先 | なぜ |
|---|----|----|
|レイヤー|人| - |
|観点|変更容易性・安定性・運用費用|プロのいない現場は悲惨|
|影響|BC・柔軟な変化・スキル|今以上を求めることは難しい|

---

#### 対処方法
- 返済：教育の充実、テックリードの創出
- 自転車操業：事業の縮小、外部ソフトハウスの利用

---

## 実は技術的負債ではない例

---

### ほとんど使われないシステム
- テストがなくても今動いていれば大丈夫
- 改修するくらいなら捨てる
    - 徳政令

---

### 立派な既製品があるシステム
- 自前主義を捨てて既製品を利用する
- 実際に乗り換えなくても、選択肢があることが重要

---

### モノリシックなシステム
- イメージを取るだけで移行できるなら、選択肢の一つ
- 多くのAPI群にすると管理が圧迫される。[参考](http://postd.cc/the-end-of-microservices/)
- 場合による

---

### ローマ字変数
- kubun
    - 区分は別の意味で問題が・・・
- rieki
- yakushoku

ダサいけど

---

### そのやり方に対価を得ている
- 重厚な仕様書が納品に必要
- 仕様書と実装の乖離が負債の可能性となっても、そういうビジネスモデルだから

---

# あなたの事業にとって何が問題かを知る

- この記事を読んでいるエンジニアは、負債の匂いを感じられる人であると考えられる。
- さらなる匂いに気づきたければ、勉強会に出よう。
- 問題の種類を自ら分類しよう。
    - その匂いはきっと本物だが、問題なのか
    - ソムリエではない自分には、ワインの保存状態を匂いで（そしてきっと味でも）わからない
- 問題を多くの人と共有しよう。

---

# コラム：エンジニアは課題解決が好物

- エンジニアは問題を解決するためにスキルを得る志向が強い。
- 目の前に問題があれば解決したくなる。
- 問題を放置しておくことに将来的な不安を強く持ちがち。

けど

---

- **YAGNI** は余計な新機能にのみ適用されるものではない。
- 総合的な判断で先延ばしも許そう。
- あなたには、目の前の問題を解決する以上の価値があるかもしれない。

---

# 問題に対する解決策とROI

- 問題を共有する際には、それがなぜ問題なのかを、共有する相手にわかるように伝える。
- 問題の解決方法も自分なりに持って行く。
- そのときにどれくらいのエネルギー・金の投入が必要か。
- 解決することで得られるものは何なのか。

冷静に分析しよう。

---

# まとめ
- 解決すべき問題は無数にある
  - 残念ながら金も人も時間も有限だ
- エンジニアの「やりたい」を分析する
  - エンジニア自身：ただやりたいだけか、何を得られるか
  - 事業者も：なぜそれが必要なのか、真剣に耳を傾ける
- 解決策は好き嫌いで決めない
  - 安定性・速度のためにElixir/Phoenixを選ぶ？
  - 俺が倒れても任せられる組織か？
- あなたと嗅覚の違うプロジェクトは、あなたには合わない
    - 嗅覚を一緒にする（意識を統一する）か、匂いに鈍感になるか

---