Skip to content

Instantly share code, notes, and snippets.

@pgr0ss
Created October 3, 2013 04:34
Show Gist options
  • Save pgr0ss/2f2283a81c40f41d48c9 to your computer and use it in GitHub Desktop.
Save pgr0ss/2f2283a81c40f41d48c9 to your computer and use it in GitHub Desktop.
ActiveRecord::SpawnMethods::VALID_FIND_OPTIONS << :allow_unscoped_find
ActiveRecord::Base.class_eval do
def self.allow_unscoped_find(&block)
if block
temporarily_change_ivar("@allow_unscoped_find", true) do
yield
end
else
relation.allow_unscoped_find
end
end
def self.allow_unscoped_find?
@allow_unscoped_find
end
end
ActiveRecord::SpawnMethods.class_eval do
def apply_finder_options_with_scoped_find_check(options)
result = apply_finder_options_without_scoped_find_check(options)
if options[:allow_unscoped_find]
result.instance_variable_set("@allow_unscoped_find", true)
end
result
end
alias_method_chain :apply_finder_options, :scoped_find_check
def except_with_scoped_find_check(*args)
except_without_scoped_find_check(*args).tap do |result|
_copy_allow_unscoped_ivar(self, result)
end
end
alias_method_chain :except, :scoped_find_check
def merge_with_scoped_find_check(relation)
merge_without_scoped_find_check(relation).tap do |result|
_copy_allow_unscoped_ivar(relation, result)
end
end
alias_method_chain :merge, :scoped_find_check
def only_with_scoped_find_check(*args)
only_without_scoped_find_check(*args).tap do |result|
_copy_allow_unscoped_ivar(self, result)
end
end
alias_method_chain :only, :scoped_find_check
def _copy_allow_unscoped_ivar(from, to)
if from.instance_variable_get("@allow_unscoped_find")
to.instance_variable_set("@allow_unscoped_find", true)
end
end
end
ActiveRecord::Relation.class_eval do
attr_accessor :allow_unscoped_find
def allow_unscoped_find
relation = clone
relation.allow_unscoped_find = true
relation
end
def to_a_with_scoped_find_check
sql = arel.to_sql
unless _has_valid_conditions?(sql)
raise RuntimeError, "#finds must be scoped on #{@klass.to_s}"
end
to_a_without_scoped_find_check
end
alias_method_chain :to_a, :scoped_find_check
def _has_valid_conditions?(sql)
@allow_unscoped_find || @klass.allow_unscoped_find? || _whitelisted_models.include?(@klass.to_s) || _valid_string_conditions?(sql) || false
end
def _valid_string_conditions?(conditions)
conditions =~ /_id"? (=|IN|IS)/ || conditions =~ /"?\w+"?\."?id"? (=|IN)/
end
def _whitelisted_models
[
"Merchant",
]
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment