web-dev-qa-db-ja.com

RSpecを使用してプライベートメソッドをテストする必要がありますか?

プライベートメソッドのテストを作成することは良い習慣ですか?

次の簡単な例を考えてみましょう。

_class Group
  has_many :members

  private

  def release_members
    members.each { |member| member.update_attributes group_id: nil }
  end
end
_

RSpecでrelease_membersメソッドのテストを書くのは良い習慣でしょうか? sendieを使用してメソッドを呼び出すテストを作成する必要があると思います。 group.send(:release_members)これは時々眉をひそめます。

26
tyler.amos

サンディメッツの講演からのこれらのスライドで、まさにその主題の詳細な議論を見つけることができます。

https://speakerdeck.com/skmetz/magic-tricks-of-testing-railsconf

彼女は、必要に応じてプライベートメソッドをテストドライブすることもできますが、心配する必要があるのはパブリックインターフェイスをテストするテストだけだと言います。そうしないと、実装と緊密に結合しすぎる可能性があります。

テストされていない複雑なプライベートメソッドに神経質になっている場合は、サービスと値オブジェクトを分割してテストすることも重要だと思います。

17
Joeyjoejoejr

プライベートメソッドはクラスの内部メカニズムに属しているため、テストしないでください。単体テストの目的は、クラスがそのインターフェース、つまりパブリックメソッドを介して対話するときに期待どおりに動作することを確認することです。

ある時点で長いプライベートメソッドに慣れていない場合は、おそらくここでそのロジックをクラスの外に引き出して別のモジュールまたはクラスを構築する機会があるためです。次に、それをユニットテストできます。これも、そのインターフェイス、つまりパブリックメソッドのみです。

まれに、内部ロジック全体が非常に複雑で、問題を分割したいため、プライベートメソッドをテストする必要があります。しかし、99.9%では、プライベートメソッドをテストすることは悪い考えです。

29
toch