discourse-ai/spec/lib/guardian_extensions_spec.rb
Roman Rizzi 46fcdb6ba5
FIX: Make summaries backfill job more resilient. (#1071)
To quickly select backfill candidates without comparing SHAs, we compare the last summarized post to the topic's highest_post_number. However, hiding or deleting a post and adding a small action will update this column, causing the job to stall and re-generate the same summary repeatedly until someone posts a regular reply. On top of this, this is not always true for topics with `best_replies`, as this last reply isn't necessarily included.

Since this is not evident at first glance and each summarization strategy picks its targets differently, I'm opting to simplify the backfill logic and how we track potential candidates.

The first step is dropping `content_range`, which serves no purpose and it's there because summary caching was supposed to work differently at the beginning. So instead, I'm replacing it with a column called `highest_target_number`, which tracks `highest_post_number` for topics and could track other things like channel's `message_count` in the future.

Now that we have this column when selecting every potential backfill candidate, we'll check if the summary is truly outdated by comparing the SHAs, and if it's not, we just update the column and move on
2025-01-16 09:42:53 -03:00

103 lines
3.0 KiB
Ruby

# frozen_string_literal: true
describe DiscourseAi::GuardianExtensions do
fab!(:user)
fab!(:group)
fab!(:topic)
before do
group.add(user)
assign_fake_provider_to(:ai_summarization_model)
SiteSetting.ai_summarization_enabled = true
SiteSetting.ai_summary_gists_enabled = true
end
let(:anon_guardian) { Guardian.new }
let(:guardian) { Guardian.new(user) }
describe "#can_see_summary?" do
context "when the user cannot generate a summary" do
before { SiteSetting.ai_custom_summarization_allowed_groups = "" }
it "returns false" do
SiteSetting.ai_custom_summarization_allowed_groups = ""
expect(guardian.can_see_summary?(topic)).to eq(false)
end
it "returns true if there is a cached summary" do
Fabricate(:ai_summary, target: topic)
expect(guardian.can_see_summary?(topic)).to eq(true)
end
end
context "when the user can generate a summary" do
before { SiteSetting.ai_custom_summarization_allowed_groups = group.id }
it "returns true if the user group is present in the ai_custom_summarization_allowed_groups_map setting" do
expect(guardian.can_see_summary?(topic)).to eq(true)
end
end
context "when the topic is a PM" do
before { SiteSetting.ai_custom_summarization_allowed_groups = group.id }
let(:pm) { Fabricate(:private_message_topic) }
it "returns false" do
expect(guardian.can_see_summary?(pm)).to eq(false)
end
it "returns true if user is in a group that is allowed summaries" do
SiteSetting.ai_pm_summarization_allowed_groups = group.id
expect(guardian.can_see_summary?(pm)).to eq(true)
end
end
context "when there is no user" do
it "returns false for anons" do
expect(anon_guardian.can_see_summary?(topic)).to eq(false)
end
it "returns true for anons when there is a cached summary" do
Fabricate(:ai_summary, target: topic)
expect(guardian.can_see_summary?(topic)).to eq(true)
end
end
end
describe "#can_see_gists?" do
before { SiteSetting.ai_summary_gists_allowed_groups = group.id }
let(:guardian) { Guardian.new(user) }
context "when there is no user" do
it "returns false for anons" do
expect(anon_guardian.can_see_gists?).to eq(false)
end
end
context "when setting is set to everyone" do
before { SiteSetting.ai_summary_gists_allowed_groups = Group::AUTO_GROUPS[:everyone] }
it "returns true" do
expect(guardian.can_see_gists?).to eq(true)
end
end
context "when there is a user but it's not a member of the allowed groups" do
before { SiteSetting.ai_summary_gists_allowed_groups = "" }
it "returns false" do
expect(guardian.can_see_gists?).to eq(false)
end
end
context "when there is a user who is a member of an allowed group" do
it "returns false" do
expect(guardian.can_see_gists?).to eq(true)
end
end
end
end