TODOコメントの使い方

Hodagi
13 min readJan 1, 2020

Programming Kubernetesの共著者達の会話を見ながら…

最近TODOの数について言及する記事を立て続けに読んだ。

一つがKubernetesに2000個以上あるTODOコメントについてtickgitというツールを使って解析した記事である。どのコンポーネントにTODOの数が多いか、だれが残したTODOが多いかなど調査している。

一番上の神々のTwitterによるやりとりは、TODOistのTop5にstttsさんの名前があったことに端を発するものだ。Githubの芝を真っ緑に埋めるくらいKubernetes/OpenShiftで活動されなくてはこうはならないけど。

もう一つはLinux Kernelにある3000個以上あるTODOコメントの大半が10年以上前のものという記事である。(記事というか一覧化しただけだが)こちらも同じくtickgitというツールを使って解析した結果だ。

https://todos.tickgit.com/browse?repo=https://github.com/torvalds/linux

これらの記事とそれに対するHacker News、スラドのコメントを見ながらつらつらと思ったことを書いていこうと思う。

この二つの記事を見て、ぱっと思ったのがコメントとプロダクトの規模や古さが相関していないところである。

Linux Kernelは20年以上にもなる古い歴史があり、そのソースコード行数は3000万行近くになる。

対してKubernetesはOSSデビューしてから丸5年と比較的若いプロダクトといえるが、すでにそのソースコード行数は約80万行にも上る。

scc counts 4.3M+ lines of go source code (5.2M+ total lines), 3M+ lines of “actual” vs. 700k+ lines of comments. 16k+ files in total. This includes the vendor/ directory.

Linux Kernelとのソースコードの規模を比較すると、Kubernetesは若いプロダクトとしては破格の大きさだが、TODOのコメントの数がたった2/3倍というのは腑に落ちない。もっと少なくともいいはずだ。

これはKubernetesがまだまだ機能的に完成していないことを示しているのだろうか?Kubernetesの品質が暗に悪いことを示しているのだろうか?

いや、そうではないだろう。その背景にあるのは、Linux KernelとKubernetesの開発スタイルの違いだと自分は考える。

開発プロセスの違い、数の大小はあるにせよ、怖いおじさんが最後の門番となって残るLinux Kernelも、プロダクトのマイナーバージョンが3か月ごとに変わる劇的な変化を起こし続けるKubernetesも結局TODOコメントの魅力からは逃れられていない事実は興味深い。

どうして古いTODOコメントはどうして残ってしまうのだろうか?

どうしてTODOコメントは今も増え続けるのか?

それはプロダクトとして健康なのか?

これらの疑問にこたえるべく、まずはどのようなときにTODOコメントをつけばいいか?あるべき論を見ていこうと思う。

Robert C. Martinさんによる名著”Clean Code” を紐解いてみた。
彼はコメントについてわざわざ第四章を割いて説明している。

Comments are not like Schindler’s List. They are not “pure good.” Indeed, comments are, at best, a necessary evil.

訳: コメントは”シンドラーのリスト”のようなものではない。”純粋な善”ではない。実際、コメントはせいぜい必要悪だ。

コメントに対しては否定的な立場とわかる。自分自身を説明する表現をソースコードでできなかった場合にのみコメントは使うべきだと彼は説明する。

そうすると、”これから”を表現するTODOコメントはどうなのだろうか?幼稚園児の息子がいたとして、注釈無しに大人になった姿を容易に想像できるか?

It is sometimes reasonable to leave “To do” notes in the form of //TODO comments. In the following case, the TODO comment explains why the function has a degenerate implementation and what that function’s future should be.

訳: TODOコメントの形式で “To do”を残すことが妥当なケースがあります。
下記のケースではTODOコメントにより関数がいつかなくなること、そして関数の未来について説明しています。

// TODO-MdM these are not needed
// We expect this to go away when we do the checkout model

protected VersionInfo makeVersion() throws Exception
{
return null;
}

TODOコメントを書かざるを得ない状況は次のことが考えられる。

・プログラマーがやるべきだと思う仕事だが、何らかの理由で現時点ではできない場合
・Deprecatedになった機能をどこかのタイミングで削除することをリマインドさせたい場合
・自分には手に負えない問題を誰かに見てもらうようにする場合
・他の誰かにより良い名前を考えてもらうようにする場合
・今後予定しているロードマップに合わせて依存部分の変更を行うようにリマインドさせたい場合

ただし、他にどんなにTODOで仮置きしたいことがあって、システムに悪いコードを残すための言い訳にはならないとMatinさんは言う。

自分の脳裏に浮かんだクソコード…もとい悪いコードの例を挙げておこう。

// TODO: いつかやる
protected Metrics makeSummary() throws Exception
{
// 実例ではないですよ、ええ全く!!
return (Metrics) new Object();
}

Matinさんは今どきのIDEにはTODOを見つけるための機能が備わっているが、それでもTODOコメントがそこら中に散らばるのはよくないし、定期的にTODOをスキャンし、消すべきだと締めくくっている。

Matinさんの意見からコメントはそもそもソースコードが自分自身を十分に説明できないときの補足として使うという原則論を学んだ。
その中でもTODOは未来に向けたメッセージであることを知った。

割とこの辺は肌身に感じている人も多いのではないか?一年前に書いたソースコードは基本的に別人が書いたそれと見分けがつかない。一年前の自分からの通信手段がTODOコメントなのだ。

理論を学んだところで、Hacker Newsのjonny387さんのtopコメントから、なぜプログラマはTODOをつけるのか、どういうときにTODOをつけているのか…それによって実際に感じているメリットを見てみよう。

TODO is vital for my development process. Sure, maybe there’s better programmers who don’t use or need TODO, but for me, it’s a critical method for the following reasons.

TODOは私の開発プロセスに欠かせません。確かにTODOを使用しない、必要としない良いプログラマーはいますが、私にとっては下記の理由からTODOコメントは重要な方法です。

1. It prevents my “flow” from being sidetracked by micro-optimizations that are probably too early to consider necessary anyway.

考えるにはおそらく早すぎるmicro-optimizationsによって”フロー”が本筋から離れるのを防ぎます。

2. It helps me to retain my short term on the code I am working on. If I branched out at each TODO to implement some improvement or method, my brain typically needs to context switch to focus on the fine details of the subject. By the time this is done, and I switch back, I have forgotten key aspects of what I was working on and it slows me down again (i.e. local names, structs, etc.)

作業中のソースコードを短期間記憶しておくのに役立ちます。
何らかの改善やメソッドの実装のためにあちこちの分岐条件にTODOをつけた場合、私の脳は対象の詳細に焦点を合わせるためにコンテキストを切り替える必要があります。

3. It allows me to re-approach something with a completely different mind set (given that I come back to it after a significant amount of times). Half the time I realise that what I wrote was indeed “good enough” and no further time should be committed to it unless a reason exists to do so.

(かなりの時間をかけて戻ってきた場合に)まったく異なる考え方で再アプローチすることができます。また、自分が書いたものが”十分”であり、そうする時間がない限り、それ以上時間を費やすべきでないことを(TODOコメントにより)、半分の時間でわかります。

4. It gives opportunity for other developers to see, think, comment and contribute on the subject. I find that typically if I TODO an area, it’s good for a second set of eye balls to see it. There’s far smarter people than me around, and there’s a good chance one of them will find it and propose a better solution.

他の開発者がTODOコメントを見て、考え、コメントして、コントリビュートする機会を与えます。もしTODOをつけるとき、異なる視点から見るのが良いと思います。周りには自分よりもはるかに頭がいい人たちがいるので、そのうちの一人がTODOコメントを見つけた時、より良い解決策を提案する可能性が十分にあります。

5. On the rare “quiet” day, I can grep for TODO and just work through them.

めったにない”静かな”日には、TODOをgrepして、こなしていくことができます。

こうして俯瞰してみると、TODOのタグ一つが、実に多くの意味合いを持つことがわかる。それは単純なアノテーションなどではなく、未来の自分への通知であり、他の人に知らせるサインであり、脳内メモリの外部装置なのだ。

ここにTODOが少なくとも忘れ去られてしまう理由があると自分は思う。たくさんの意味合いがある中でどの文脈でTODOで使ったのかは実際にソースコードを実装して記録を残した人にしかわからない。そして本人すらも一年もすれば、どうしてそのコメントを書いたのか忘れてしまうのだ。

TODOコメントの是非はここでは問わない。TODOコメントは消し忘れさえなければ、上記の理由により、非常に有益だと自分も思うからだ。それゆえ、消し忘れを避ける方法として三つ提案したい。

TODOのタグをもっと細かくする

Hacker Newsのコメントにあるが、複数の意味合いがTODOコメントにあるならば、 FIXME、HACK、NOTEなどタグも細かくするのは手だ。

FIXME — PoC以外で、(プロダクトリリース時には)実際にコミットするべきではない。直して!!

TODO — 製品リリース前にはできれば、いつか修正すべき

NOTE — 備考: このケースの場合に関する検証が不足している

HACK — 特定の問題を修正するために無理やり筋を通した。いつか直す
https://stackoverflow.com/questions/14366182/usage-of-hack-and-undone-comment-tags

REVIEW — もっといい感じにしたいけど再考よろ

OPTIMIZE —”静かな”日に修正できたらいいな

TODOのうち、レビューの意味合いが含まれる内容はissueに起こせ

上記のタグと方針が少し異なるが、REVIEWの意味合いがあるTODOコメントはチケット管理を行っているならissueにした方がより周知されやすいと思う。

OSSではないプロダクトをチームで作っていて、機能ごとに開発者が分かれていた場合、レビュー以外で偶然ソースコードを見てなおかついいアイディアを思いつきPRまでちゃんと書いてくれるような親切な人が現れるセレンディピティを期待するのは、これを書いている自分に良い人が来てくれると期待するくらい酷なことだろう。

プロダクトのライフサイクルに合わせてTODOを強制削除する

TODOコメントが許されるのはいつまでか?

個人的にはプロダクトのライフサイクルに合わせるべきだと思う。メジャーバージョンの更新…を待っていると時間がかかるので、基本的にはマイナーバージョンのEOLにTODOコメントのライフサイクルを合わせるべきか?git blameとk8s botの組み合わせツールがでてくることを望む。

新幹線での長時間が暇すぎて、とりとめもなくTODOコメントについて語ってしまった。

TODOコメントに関してこういう運用をしているという人がいらっしゃったら意見を聞きたい。

--

--