こんにちは、私の名前はLeonidで、Align TechnologyのRuby on Railsを使用してチームで働いています。
仕事では、RSpecとともにレールを使用します。今日は、テストで独自のタグを使用して自分の生活を楽にする方法に関する経験を共有します。
デフォルトでは、レールのRSPECには、テスト対象に応じてテストをグループ化するための複数のディレクトリがあります。モデル、個別のコントローラ、ビュー、複数のコントローラ、ルーティングです。
内部では、rspecはタグ(メタデータ)を付加します。これにより、あるグループのテストを補助メソッドと新しいアサーションで補完します。 (メタデータは、各フォルダーがこのテストにこのディレクトリの名前を持つタイプキーを追加する単なるハッシュです)
起動の各テストは、独自に生成されたクラスを受け取ります。実際には、DSLモジュールと必要なヘルパーおよびアサーションが混在しています。
テストで満たす必要があるプロパティで特定のディレクトリに配置できない場合は、独自のタグを使用できます。
以下は、作業で使用する便利なタグです。
検索エンジン(Sunspotなど)の動作を制御します
通常、railsの検索ライブラリはActiveRecord / ActiveModelクラスと統合され、インデックス付きフィールドを構成するDSLメソッドを呼び出してafter_saveコールバックを設定します。
同時に、人気のある検索ライブラリの1つであるSunspotには、rspekとの自動統合がありません。つまり、テストでは常にモデルのインデックスが作成されます。 ほとんどの場合、これはテストを大幅に遅くします。これは、検索エンジンの正しい構成として、通常、検索コントローラーのテストでのみ使用され、たとえば同義語やランキングテストで使用されるためです。
必要な場合にのみ検索エンジンにデータを送信することを含むルールタグを追加しましょう。
spec / spec_helper.rb:
# --- :solr tag --- # By default, Sunspot engine is disabled in any tests, with its connection stubbed. # Add :solr tag to enable regular model indexing. # Don't forget to run your search engine by corresponding rake task before running the suite. config.before :suite do $real_solr_session = ::Sunspot.session ::Sunspot.session = ::Sunspot::Rails::StubSessionProxy.new(::Sunspot.session) end config.before :each, solr: true do ::Sunspot.session = $real_solr_session end config.after :each, solr: true do $real_solr_session = ::Sunspot.session ::Sunspot.session = ::Sunspot::Rails::StubSessionProxy.new(::Sunspot.session) end
ここで、検索エンジンを本当に必要とするテストにsolrタグを付けてください 。
たとえば、synonyms.txtの同義語が正しく機能するかどうかを確認します。
スペック/モデル/ document.rb
it 'knows that tienda means store, in case someone will use \'STORE\' among spanish documents' do FactoryGirl.create :document, title: 'Lorem ipsum store dolor sit amet', searchable: true, locales: Locale.find_by(name:'es') Document.reindex Document.solr_search { fulltext 'tienda' }.hits.should have(1).document_match Document.solr_search { fulltext 'store' }.hits.should have(1).document_match end
移行およびライブデータのテスト:フィクスチャとしてのデータベース。
実際、「小さな」データベースを持つアプリケーションの場合、データベース全体を「テストデータセット」の1つとして使用することを妨げるものは何もありません。
これにより、複雑な移行をテストするだけでなく、実際のデータでアサーションを作成できます。
そのため、ライブDBスナップショットで始まる:シードタグには、いくつかのものが必要です。 1つ目は、Rakeタスクです。Rakeタスクは、データベースの新しいスナップショットを取得し(たとえば、1日に1回取得します)、必要に応じて重要な運用データを消去します。
2番目のポイントは次のとおりです。データベースの復元には時間がかかるため、最初にすべての「通常の」テストを実行してから、最後に実行されるように「フル」データベースでテストをグループ化します。
spec / spec_helper.rb:
config.order_groups {|list| list.reject{|e| e.metadata[:seeded]}.shuffle(random: Random.new(config.seed)) \ + list.select{|e| e.metadata[:seeded]}.shuffle }
(トランザクションのテストを実行するための通常のメカニズムを使用する方が良いでしょう。これはテストの終了時にキャンセルされます)
Rspecは、ランダムな順序でテストを実行して、前のテストで破損した状態の問題を見つけようとすることに注意してください。 (この後、起動時に出力する値に--seededフラグを渡すと、同じ順序でデバッグが可能になります)したがって、合意に従って乱数ジェネレーターをconfig.seed rsppekにリセットします。
タグ自体のルールを設定することは残ります。
spec / spec_helper.rb:
# --- :seeded tag --- # 1. have all :seeded tags grouped and executed at the end of the test suite # 2. have your SQL test DB filled with fresh data from content master # 3. then migrated from your migrations # REQUIREMENTS: # A. all :seeded tests run one after another # B. :seeded tag is put on the top 'describe' blocks config.before :all, seeded: true do unless $rspec_seeded_database Rails.application.load_tasks Rake::Task['db:restore_from_snapshot '].invoke Rake::Task['db:migrate'].invoke $rspec_seeded_database = true Rails.application.reload_routes! #Rake::Task['sunspot:reindex'].invoke end end config.after :all, seeded: true do end
同時に、db:restore_from_snapshot rakeタスクでは、ダウンロードしたデータベーススナップショットをtmp /フォルダーにキャッシュして、開発者のマシンに毎回ダウンロードしないようにします。
デプロイされたアプリケーションのテスト
さらに良いことは、同じ要求テストを使用して、稼働中のアプリケーションをテストできることです。 もちろん、これは、データベースでまったく機能しない場合、または展開されたサーバーと同じデータをデータベースから読み取る場合にのみ可能です。
タグを書きます:
spec / spec_helper.rb:
config.before :each, also_for_smoke_test: :true do Capybara.run_server = false Capybara.app_host = ENV['ACCEPTANCE_URL'] Capybara.current_driver = :webkit end
ここで、テストの必要な部分のみを煙テストスクリプトとして実行します。
ACCEPTANCE_URL=https://your-host.com rspec -t also_for_smoke_test
どのルールタグを使用しますか?