Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions lib/ransack/nodes/condition.rb
Original file line number Diff line number Diff line change
Expand Up @@ -235,11 +235,21 @@ def formatted_values_for_attribute(attr)
val = attr.ransacker.formatter.call(val)
end
val = predicate.format(val)

# Handle case where formatter for IN/NOT IN predicates returns a string with comma-separated values
if predicate.wants_array && val.is_a?(String) && val.include?("','")
val = val.split("','")
end

if val.is_a?(String) && val.include?('%')
val = Arel::Nodes::Quoted.new(val)
end
val
end

# Flatten the array in case any formatters returned arrays
formatted = formatted.flatten if predicate.wants_array

if predicate.wants_array
formatted
else
Expand Down
19 changes: 19 additions & 0 deletions spec/ransack/predicate_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -473,6 +473,25 @@ module Ransack
expect(@s.result.to_sql).to match /#{field} NOT IN \('a', 'b'\)/
end
end

describe "with 'in' arel predicate and string formatter" do
before do
Ransack.configure do |config|
config.add_predicate 'in_list',
arel_predicate: 'in',
formatter: ->(v) { v&.split(';').join("','") }
end
end

it 'generates correct IN clause without extra quotes' do
@s.name_in_list = 'test;othertest'
field = "#{quote_table_name("people")}.#{quote_column_name("name")}"
# Should generate: WHERE people.name IN ('test', 'othertest')
# Not: WHERE people.name IN ('test'',''othertest')
expect(@s.result.to_sql).to match /#{field} IN \('test', 'othertest'\)/
expect(@s.result.to_sql).not_to match /#{field} IN \('test'',''othertest'\)/
end
end
end

private
Expand Down
Loading