/usr/lib/ruby/vendor_ruby/sequel/extensions/split_array_nil.rb is in ruby-sequel 4.1.1-1.
This file is owned by root:root, with mode 0o644.
The actual contents of the file can be viewed below.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 | # The split_array_nil extension overrides Sequel's default handling of
# IN/NOT IN with arrays of values to do specific nil checking. For example,
#
# ds = DB[:table].where(:column=>[1, nil])
#
# By default, that produces the following SQL:
#
# SELECT * FROM table WHERE (column IN (1, NULL))
#
# However, because NULL = NULL is not true in SQL (it is NULL), this
# will not return rows in the table where the column is NULL. This
# extension allows for an alternative behavior more similar to ruby,
# which will return rows in the table where the column is NULL, using
# a query like:
#
# SELECT * FROM table WHERE ((column IN (1)) OR (column IS NULL)))
#
# Similarly, for NOT IN queries:
#
# ds = DB[:table].exclude(:column=>[1, nil])
# # Default:
# # SELECT * FROM table WHERE (column NOT IN (1, NULL))
# # with split_array_nils extension:
# # SELECT * FROM table WHERE ((column NOT IN (1)) AND (column IS NOT NULL)))
#
# To use this extension with a single dataset:
#
# ds = ds.extension(:split_array_nil)
#
# To use this extension for all of a database's datasets:
#
# DB.extension(:split_array_nil)
module Sequel
class Dataset
module SplitArrayNil
# Over the IN/NOT IN handling with an array of values where one of the
# values in the array is nil, by removing nils from the array of values,
# and using a separate OR IS NULL clause for IN or AND IS NOT NULL clause
# for NOT IN.
def complex_expression_sql_append(sql, op, args)
case op
when :IN, :"NOT IN"
vals = args.at(1)
if vals.is_a?(Array) && vals.any?{|v| v.nil?}
cols = args.at(0)
vals = vals.compact
c = Sequel::SQL::BooleanExpression
if op == :IN
literal_append(sql, c.new(:OR, c.new(:IN, cols, vals), c.new(:IS, cols, nil)))
else
literal_append(sql, c.new(:AND, c.new(:"NOT IN", cols, vals), c.new(:"IS NOT", cols, nil)))
end
else
super
end
else
super
end
end
end
end
Dataset.register_extension(:split_array_nil, Dataset::SplitArrayNil)
end
|