🏥
Gem のメンテナンスが行われているかを確認するコマンド bundler-alive を作った
これはなに?
bundler-alive は「Ruby の Gemfile.lock に記載された gem がメンテナンスされているか」を確認するコマンドです[1]。
次はインストールと実行例です。
# インストール
$ gem install bundler-alive
# 実行
$ bundle-alive
Name: journey
URL: http://github.com/rails/journey
Status: false
Not alive gems are found!
かんたんな流れは次のようになっています。
- Ruby の
Gemfile.lock
をパースする - RubyGems.org から該当の gem の情報を取得する
- gem のソースコードリポジトリからメンテナンス状況を確認する
- アーカイブされていればレポートする
CI などに組み込んで、定期的にチェックできる事を目指しています。
きっかけ
良いコード/悪いコードで学ぶ設計入門 を読んで、実践したらどんな感じなのか試してみようと思ったのがきっかけです[2]。
この書籍の中では、得た知見を普段のプロダクションコードで試す事を勧めていましたが、自分がコントロールできるものが良かったので、ツールを作って試してみました。
実践できた(かもしれない)ところ
結果として、静的解析ツール Rubocop のサポートによるところが大きいかもしれません。
- 「3.1 クラス単体で正常に動作するよう設計する」
- これまでこの意識がうすかった
- 「5.5 多すぎる引数」の抑制
- Rubocop でチェックした
- 「5.5.1 プリミティブ型執着」の回避
- Ruby のようなコンパイラの無い言語だとちょっと冗長になる気がする
- 呼び出されたメソッド側で、型(オブジェクト)チェックが常に必要?
- コンパイラのチェックが無いのでメリットを一部しか享受できない
- クラスがすぐに増えすぎる懸念もある
- しかし、それでもメリットは大きいと思う
- Ruby のようなコンパイラの無い言語だとちょっと冗長になる気がする
- 「5.6.1 尋ねるな、命じろ」
- これまでなんとなくぐらいの意識しかなくて、「決め」の問題だと思っていた
- 尋ねる場合、すべての呼び出し場所で尋ねる必要があるのでイマイチだな、程度
- なので、場所によって尋ねてしまっていた箇所があった
- これまでなんとなくぐらいの意識しかなくて、「決め」の問題だと思っていた
- 「6.1.1 早期 return でネスト解消」の実施
- これは普段から気をつけている
- 「6.2.7 interface を switch 文重複に応用」
- ソースコードリポジトリの分岐箇所
- 現状は GitHub のみしかサポートしていないけれど、他のサービスへの拡張を意識した
- Ruby にはインターフェースがないが、「switch の代わりに Map で切り替える」を参考にハッシュとダックタイプで実現した
- 過去に同様の実装をした事があるが、逆にハッシュによる変換が分かりづらくなってしまい、レビューアと相談して辞めた事がある
- 今回はむしろ導入した方が良かった
- ソースコードリポジトリの分岐箇所
- 「9.1 デッドコード」
- Rubocop でチェックした
- 「10.4.1 技術駆動命名」の回避
- 結果を TOML ファイルに保存していて、最初
toml_file
とか付けていた - ハッシュを
hash
と付けている箇所があるので改善の余地あり
- 結果を TOML ファイルに保存していて、最初
さいごに
bundler-alive
はまだ実験的要素が大きく、課題もたくさんあります。
- 対象の gem が多いと GitHub API の rate limit にかかりやすい
- パーソナルアクセストークンを使ってもツラい
- 認証済みアプリのトークンが使えないか
- 複数のリポジトリを一度に取得できないか
- BigQuery のパブリックデータ GH Archive が使えないか
- 対象のソースコードリポジトリが GitHub しかサポートしていない
- GitLab とかサポートしたい
- 「アーカイブ済か」のみチェックしている
- 例えば最終コミット日時も考慮した方が良いのではないか?
などなど。これらは今後改善していきたいと思っています。
また、思い起こせば、これまで保守がしづらいコードをたくさんメンテしてきました。それらはすべて前任者から引き継いだものではなく、自分も悪いコードを書いてきた自覚が十分にあります。
既存の悪いコードに対して悪態をつくのは、良いコードを書くよりとてもかんたんです[3]。
既存のコードをメンテするにしろ、新しく書くにしろ、なるべく保守しやすい良いコードを書いていきたいと思っています。
Discussion