Files
old-gem/spec/lib/text_to_sql_query_spec.rb
2020-02-10 15:16:57 +01:00

67 lines
5.9 KiB
Ruby

# frozen_string_literal: true
require_relative '../../lib/text_to_sql_query'
describe TextToSqlQuery do
describe '.new' do
# tests simple search term without column name and without quotes
it { expect(described_class.new('some-default-value', [:"players.name"], :"players.name").where_clause).to eq(['players.name ILIKE ?', '%some-default-value%']) }
# tests simple search term with column name and without quotes
it { expect(described_class.new('name:ab', [:"players.name"], :"players.name").where_clause).to eq(['players.name ILIKE ?', '%ab%']) }
# tests simple search term with unknown column name and without quotes
it { expect{described_class.new('unknown:ab', [:"players.name"], :"players.name").where_clause}.to raise_error(RuntimeError, "Unknown field 'unknown'") }
# tests simple search term without column name and with quotes
it { expect(described_class.new('"ab"', [:"players.name", :"players.device_id"], :"players.device_id").where_clause).to eq(["players.device_id ILIKE ?", "%ab%"]) }
# tests simple search term with column name and with quotes
it { expect(described_class.new('tags:"ab"', [:"players.name", :"players.tags"], :"players.device_id").where_clause).to eq(["players.tags ILIKE ?", "%ab%"]) }
# tests search without operators
it { expect(described_class.new('123 456', [:"players.name", :"players.device_id"], :"players.device_id").where_clause).to eq(["(players.device_id ILIKE ? OR players.device_id ILIKE ?)", "%123%", "%456%"]) }
# tests search with OR operator
it { expect(described_class.new('123 or 456', [:"players.name", :"players.device_id"], :"players.device_id").where_clause).to eq(["(players.device_id ILIKE ? OR players.device_id ILIKE ?)", "%123%", "%456%"]) }
# tests search with AND operator
it { expect(described_class.new('123 and 456', [:"players.name", :"players.device_id"], :"players.device_id").where_clause).to eq(["(players.device_id ILIKE ? AND players.device_id ILIKE ?)", "%123%", "%456%"]) }
# tests search with NOT operator on default column
it { expect(described_class.new('not 23', [:"players.name", :"players.device_id"], :"players.device_id").where_clause).to eq(["NOT players.device_id ILIKE ?", "%23%"]) }
# tests search with NOT operator on non-default column
it { expect(described_class.new('not value:23', [:"players.name", :"players.value"], :"players.device_id").where_clause).to eq(["NOT players.value ILIKE ?", "%23%"]) }
# tests search with mixed logical operators
it { expect(described_class.new('name:ab and not value:hf-1', [:"players.name", :"players.value"], :"players.device_id").where_clause).to eq(['(players.name ILIKE ? AND NOT players.value ILIKE ?)', '%ab%', '%hf-1%']) }
# tests search with mixed logical operators without NOT'
it { expect(described_class.new('name:a and name:b or name:c', [:"players.name", :"players.value"], :"players.device_id").where_clause).to eq(['((players.name ILIKE ? AND players.name ILIKE ?) OR players.name ILIKE ?)', '%a%', '%b%', '%c%']) }
# tests search with brackets in expression
it { expect(described_class.new('name:a and (name:b or name:c)', [:"players.name", :"players.value"], :"players.device_id").where_clause).to eq(['(players.name ILIKE ? AND (players.name ILIKE ? OR players.name ILIKE ?))', '%a%', '%b%', '%c%']) }
# tests search with brackets in expression and with NOT operator
it { expect(described_class.new('name:a and not (name:b or name:c)', [:"players.name", :"players.value"], :"players.device_id").where_clause).to eq(['(players.name ILIKE ? AND NOT (players.name ILIKE ? OR players.name ILIKE ?))', '%a%', '%b%', '%c%']) }
# tests search with special characters in search term
it { expect(described_class.new('name:"%a_\"', [:"players.name", :"players.value"], :"players.device_id").where_clause).to eq(['players.name ILIKE ?', '%\%a\_\\%']) }
# tests search with field mappings
it { expect(described_class.new('tags:h1-r', [:'players.name', :'players.value', :'players.device_id'], :"players.device_id", { tags: "tags.value" }).where_clause).to eq(['tags.value ILIKE ?', '%h1-r%']) }
# tests search with field mappings when fields array has same mapping
it { expect(described_class.new('tags:h1-r', [:'players.name', :'players.tags', :'players.device_id'], :"players.device_id", { tags: "tags.value" }).where_clause).to eq(["tags.value ILIKE ?", "%h1-r%"]) }
# tests complex query
it { expect(described_class.new('(device_id:"with space" tags:mta no-quotes-id-123) or "id with quotes-5" and ( ("id with q 10" or "id with q 20") and ("id with Q 30" "id with Q 40") and not id-without-Q-50)', [:'players.name', :'players.value', :'players.device_id'], :"players.device_id", { tags: 'tags.name' }).where_clause).to eq(['((players.device_id ILIKE ? OR (tags.name ILIKE ? OR players.device_id ILIKE ?)) OR (players.device_id ILIKE ? AND (((players.device_id ILIKE ? OR players.device_id ILIKE ?) AND (players.device_id ILIKE ? OR players.device_id ILIKE ?)) AND NOT players.device_id ILIKE ?)))', '%with space%', '%mta%', '%no-quotes-id-123%', '%id with quotes-5%', '%id with q 10%', '%id with q 20%', '%id with Q 30%', '%id with Q 40%', '%id-without-Q-50%']) }
# tests query with multiple search terms with mixed and-or-not after dash and underscore
it { expect(described_class.new('123-and-456 -or-2 -not_not_1', [:'players.title', :'players.tag', :'players.device_id'], :'players.device_id').where_clause).to eq(['(players.device_id ILIKE ? OR (players.device_id ILIKE ? OR players.device_id ILIKE ?))', '%123-and-456%', '%-or-2%', '%-not\_not\_1%'])}
# tests query with multiple search terms with mixed and-or-not after dash and underscore
it { expect(described_class.new('andrew or ornela', [:'players.title', :'players.tag', :'players.device_id'], :'players.device_id').where_clause).to eq(['(players.device_id ILIKE ? OR players.device_id ILIKE ?)', '%andrew%', '%ornela%'])}
end
end