Using Rails 7.0's #invert_where Safely
— 5 minute read
Rails 7.0 introduces the
ActiveRecord::QueryMethods#invert_where
method on ActiveRecord
query chains, and at a glance this looks like a more elegant solution to the
problem I’ve addressed previously of negating ActiveRecord scopes using
Arel. But it has one distinct and dangerous difference: in its current
implementation, it inverts all preceding conditions in the query,
including those contained within scopes — including the default scope of a
model. The consequence of this is that chaining scopes, where just one scope or
condition includes #invert_where
, will give different results for different
orderings of the chain. There is, however, a way to use it safely
while also improving my previous .not
scope implementation (and fixing a minor
bug with it that I discovered while working on the example repo for this post).