18

私のモデルにはdefault_scope(:order =>'created_at')があります。私のテスト(rspec、factory girl、shouldaなど)は次のとおりです。

require 'spec/spec_helper.rb'

describe CatMembership do
  context "is valid" do
    subject { Factory.build(:cat_membership) }
    it { should be_valid }
    it { should belong_to :cat}
    it { should belong_to :cat_group}
    it { should have_db_column(:start_date)}
    it { should have_db_column(:end_date)}
  end
end
4

3 に答える 3

30

クエリを使用して結果を確認することでこれをテストしたいのですが、本当に実行する必要がある場合、考えられる解決策の1つは、Rails3の場合のようになります。

CatMembership.scoped.to_sql.should == CatMembership.order(:created_at).to_sql

そしてレール2:

CatMembership.default_scoping.should == [{:create=>{}, :find=>{:order=>"created_at"}}]

しかし、これらのソリューションは実装に関する多くの知識を示しているため、理想的とは言えません(そして、実装はRailsのバージョンによって異なることがわかります)。

サンプルデータを作成し、通常のすべてのクエリを実行し、結果が正しく順序付けられていることを確認する方が簡単で、実際の単体テストに近く、Railsバージョンをアップグレードしても機能します。

この場合、次のようになります。

before do
  @memberships = []

  @memberships << CatMembership.create!
  @memberships << CatMembership.create!
  @memberships << CatMembership.create!

  [ 1.hour.ago, 5.minutes.ago, 1.minute.ago ].each_with_index do |time, index|
    membership = @memberships[index]
    membership.created_at = time
    membership.save
  end

end

it 'should be correctly ordered' do
  @sorted_memberships = CatMembership.all
  @memberships.first.should == @sorted_memberships.last
  @memberships.second.should == @sorted_memberships.second
  @memberships.third.should == @sorted_memberships.first
end

これははるかに冗長ですが、レールを進んでも機能します。

そして今、私は誰が質問をしたかに気づきました:D

于 2011-07-28T03:54:01.177 に答える
3

それを乾かし、共有例を使用する

ほとんどの場合、同様のデフォルトスコープを持つ複数のモデルがあるため(そうでない場合は、ほとんどこのメソッドを無視します)、このRspecの例をshared_exampleに入れて、さまざまなモデル仕様から呼び出すことができます。

デフォルトのスコープをチェックする私の好ましい方法は、次のように、デフォルトActiveRecord::Relationに期待される句(orderまたはwhere場合によっては何でも)があることを確認することです。

spec / support / shared_examples / default_scope_examples.rb

shared_examples_for 'a default scope ordered by created_at' do

  it 'adds a clause to order by created_at' do
    described_class.scoped.order_clauses.should include("created_at")
  end

end

そして、あなたのCatMembershipスペック(そして同じデフォルトスコープを持つ他のスペック)では、あなたがする必要があるのは:

spec / models / cat_membership_spec.rb

describe CatMembership

  it_behaves_like 'a default scope ordered by created_at'

  # other spec examples #

end

最後に、このパターンをあらゆる種類のデフォルトスコープに拡張し、物事をクリーンで整理された状態に保ち、何よりもDRYを維持する方法を確認できます。

于 2014-12-19T19:17:12.457 に答える
0

RSpec expectその代わりにの最新の慣習によるとshould、より良い答えは

expect(CatMembership.scoped.to_sql).to eq(CatMembership.order(:created_at).to_sql)

ただし、最近Model.scopedは非推奨になっているため、Model.all代わりに使用することをお勧めします

expect(CatMembership.all.to_sql).to eq(CatMembership.order(:created_at).to_sql)

于 2015-06-14T12:50:01.173 に答える