spec/units/search_spec.rb in es-elasticity-0.2.11 vs spec/units/search_spec.rb in es-elasticity-0.3.0

- old
+ new

@@ -1,9 +1,10 @@ require "elasticity/search" RSpec.describe "Search" do - let(:index) { double(:index) } + let(:client) { double(:client) } + let(:index_name) { "index_name" } let(:document_type) { "document" } let(:body) { {} } let :full_response do { "hits" => { "total" => 2, "hits" => [ @@ -21,34 +22,43 @@ let :empty_response do { "hits" => { "total" => 0, "hits" => [] }} end - let :highlight_response do - { "hits" => { "total" => 1, "hits" => [ - { "_id" => 1, "_source" => { "name" => "foo", "age" => 21 }, "highlight" => { "name" => "<em>foo</em>" } }, + let :scan_response do + { "_scroll_id" => "abc123", "hits" => { "total" => 2 } } + end + + let :scroll_response do + { "_scroll_id" => "abc456", "hits" => { "total" => 2, "hits" => [ + { "_id" => 1, "_source" => { "name" => "foo" } }, + { "_id" => 2, "_source" => { "name" => "bar" } }, ]}} end let :klass do Class.new do include ActiveModel::Model - attr_accessor :_id, :name, :age, :highlighted + attr_accessor :_id, :name, :age + def self.from_hit(hit) + new(_id: hit["_id"], name: hit["_source"]["name"], age: hit["_source"]["age"]) + end + def ==(other) self._id == other._id && self.name == other.name end end end - describe Elasticity::Search do + describe Elasticity::Search::Facade do subject do - described_class.new(index, document_type, body) + described_class.new(client, Elasticity::Search::Definition.new(index_name, document_type, body)) end it "searches the index and return document models" do - expect(index).to receive(:search).with(document_type, body).and_return(full_response) + expect(client).to receive(:search).with(index: index_name, type: document_type, body: body).and_return(full_response) docs = subject.documents(klass) expected = [klass.new(_id: 1, name: "foo"), klass.new(_id: 2, name: "bar")] expect(docs.total).to eq 2 @@ -62,54 +72,54 @@ expect(docs.each.first).to eq expected[0] expect(Array(docs)).to eq expected end + it "searches using scan&scroll" do + expect(client).to receive(:search).with(index: index_name, type: document_type, body: body, search_type: "scan", size: 100, scroll: "1m").and_return(scan_response) + expect(client).to receive(:scroll).with(scroll_id: "abc123", scroll: "1m").and_return(scroll_response) + expect(client).to receive(:scroll).with(scroll_id: "abc456", scroll: "1m").and_return(empty_response) + + docs = subject.scan_documents(klass) + expected = [klass.new(_id: 1, name: "foo"), klass.new(_id: 2, name: "bar")] + + expect(docs.total).to eq 2 + + expect(docs).to_not be_empty + expect(docs).to_not be_blank + + expect(Array(docs)).to eq expected + end + it "searches the index and return active record models" do - expect(index).to receive(:search).with(document_type, body.merge(_source: false)).and_return(ids_response) + expect(client).to receive(:search).with(index: index_name, type: document_type, body: body.merge(_source: false)).and_return(ids_response) relation = double(:relation, connection: double(:connection), table_name: "table_name", klass: double(:klass, primary_key: "id"), + to_sql: "SELECT * FROM table_name WHERE id IN (1)" ) allow(relation.connection).to receive(:quote_column_name) { |name| name } - expect(relation).to receive(:where).with(id: [1,2]).and_return(relation) + expect(relation).to receive(:where).with("table_name.id IN (?)", [1, 2]).and_return(relation) expect(relation).to receive(:order).with("FIELD(table_name.id,1,2)").and_return(relation) - expect(subject.active_records(relation).mapping).to be relation + expect(subject.active_records(relation).to_sql).to eq "SELECT * FROM table_name WHERE id IN (1)" end - - it "return relation.none from activerecord relation with no matches" do - expect(index).to receive(:search).with(document_type, body.merge(_source: false)).and_return(empty_response) - - relation = double(:relation) - expect(relation).to receive(:none).and_return(relation) - - expect(subject.active_records(relation).mapping).to be relation - end - - it "creates highlighted object for documents" do - expect(index).to receive(:search).with(document_type, body).and_return(highlight_response) - doc = subject.documents(klass).first - - expect(doc).to_not be_nil - expect(doc.highlighted).to eq klass.new(_id: 1, name: "<em>foo</em>", age: 21) - end end - describe Elasticity::DocumentSearchProxy do + describe Elasticity::Search::DocumentProxy do let :search do - Elasticity::Search.new(index, "document", body) + Elasticity::Search::Facade.new(client, Elasticity::Search::Definition.new(index_name, "document", body)) end subject do described_class.new(search, klass) end it "automatically maps the documents into the provided Document class" do - expect(index).to receive(:search).with(document_type, body).and_return(full_response) + expect(client).to receive(:search).with(index: index_name, type: document_type, body: body).and_return(full_response) expect(Array(subject)).to eq [klass.new(_id: 1, name: "foo"), klass.new(_id: 2, name: "bar")] end it "delegates active_records for the underlying search" do records = double(:records)