くりにっき

フルスタックキュアエンジニアです

Enumerable#all? を使う時には0件の時も考慮すべき

今日コードレビューをしてて気づいたやつ。*1

# コメントが全てお気に入り1件以上あるかどうか
comment_all_favorite = article.article_comments.all? { |article_comment| article_comment.favorite_count >= 1 }
if comment_all_favorite
  # 何か処理
end

パッと見て変哲もないコードなんですが、実は article_comments が0件の時にも上記if文の中が評価されます

サンプルコード(Ruby 2.3.0で確認)

irb(main):001:0> [].all?{ false }
=> true

空の時に all? がtrueを返すのは知らないとハマりどころかと。

日本語と英語のドキュメント両方読んでも空の時に all? が trueを返すって書いてない。。。

今回レビューしたやつは article_comments が0件の時はそもそもここの処理に入ってこないということで問題なかったのですが、もし0件の時に評価してほしくなければ

comment_all_favorite = !article.article_comments.empty? && article.article_comments.all? { |article_comment| article_comment.favorite_count >= 1 }
if comment_all_favorite
  # 何か処理
end

のように empty? も使った方がいいと思います

*1:変数名とかは変えてます