discourse/spec/support/topic_guardian_can_see_consistency_check.rb
Alan Guo Xiang Tan a473e352de
DEV: Introduce TopicGuardian#can_see_topic_ids method (#18692)
Before this commit, there was no way for us to efficiently check an
array of topics for which a user can see. Therefore, this commit
introduces the `TopicGuardian#can_see_topic_ids` method which accepts an
array of `Topic#id`s and filters out the ids which the user is not
allowed to see. The `TopicGuardian#can_see_topic_ids` method is meant to
maintain feature parity with `TopicGuardian#can_see_topic?` at all
times so a consistency check has been added in our tests to ensure that
`TopicGuardian#can_see_topic_ids` returns the same result as
`TopicGuardian#can_see_topic?`. In the near future, the plan is for us
to switch to `TopicGuardian#can_see_topic_ids` completely but I'm not
doing that in this commit as we have to be careful with the performance
impact of such a change.

This method is currently not being used in the current commit but will
be relied on in a subsequent commit.
2022-10-27 06:13:21 +08:00

45 lines
1.4 KiB
Ruby

# frozen_string_literal: true
if !Guardian.new.respond_to?(:can_see_topic?)
raise "Guardian no longer implements a `can_see_topic?` method making this consistency check invalid"
end
# Monkey patches `TopicGuardian#can_see_topic?` to ensure that `TopicGuardian#can_see_topic_ids` returns the same
# result for the same inputs. We're using this check to bridge the transition to `TopicGuardian#can_see_topic_ids` as the
# backing implementation for `TopicGuardian#can_see_topic?` in the near future.
module TopicGuardianCanSeeConsistencyCheck
extend ActiveSupport::Concern
module ClassMethods
def enable_topic_can_see_consistency_check
@enable_can_see_consistency_check = true
end
def disable_topic_can_see_consistency_check
@enable_can_see_consistency_check = false
end
def run_topic_can_see_consistency_check?
@enable_can_see_consistency_check
end
end
def can_see_topic?(topic, hide_deleted = true)
result = super
if self.class.run_topic_can_see_consistency_check?
new_result = self.can_see_topic_ids(topic_ids: [topic&.id], hide_deleted: hide_deleted).present?
if result != new_result
raise "result between TopicGuardian#can_see_topic? (#{result}) and TopicGuardian#can_see_topic_ids (#{new_result}) has drifted and returned different results for the same input"
end
end
result
end
end
class Guardian
prepend TopicGuardianCanSeeConsistencyCheck
end