2019-04-30 08:27:42 +08:00
|
|
|
# frozen_string_literal: true
|
|
|
|
|
2013-02-06 03:16:51 +08:00
|
|
|
require "promotion"
|
|
|
|
|
2022-07-28 10:27:38 +08:00
|
|
|
RSpec.describe Promotion do
|
2014-06-28 00:26:03 +08:00
|
|
|
describe "review" do
|
|
|
|
it "skips regular users" do
|
|
|
|
# Reviewing users at higher trust levels is expensive, so trigger those reviews in a background job.
|
2014-09-05 13:20:39 +08:00
|
|
|
regular = Fabricate.build(:user, trust_level: TrustLevel[2])
|
2014-06-28 00:26:03 +08:00
|
|
|
promotion = described_class.new(regular)
|
2014-09-05 13:20:39 +08:00
|
|
|
promotion.expects(:review_tl2).never
|
2014-06-28 00:26:03 +08:00
|
|
|
promotion.review
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
describe "newuser" do
|
2019-05-07 11:12:20 +08:00
|
|
|
fab!(:user) { Fabricate(:user, trust_level: TrustLevel[0], created_at: 2.days.ago) }
|
2013-02-06 03:16:51 +08:00
|
|
|
let(:promotion) { Promotion.new(user) }
|
2024-10-16 23:26:10 +08:00
|
|
|
let!(:plugin) { Plugin::Instance.new }
|
|
|
|
let!(:review_modifier) { :review_trust_level }
|
|
|
|
let!(:recalculate_modifier) { :recalculate_trust_level }
|
|
|
|
let!(:deny_block) { Proc.new { false } }
|
|
|
|
let!(:allow_block) { Proc.new { true } }
|
2013-02-06 03:16:51 +08:00
|
|
|
|
|
|
|
it "doesn't raise an error with a nil user" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect { Promotion.new(nil).review }.not_to raise_error
|
2013-02-06 03:16:51 +08:00
|
|
|
end
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
context "when user has done nothing" do
|
2013-02-06 03:16:51 +08:00
|
|
|
let!(:result) { promotion.review }
|
|
|
|
|
|
|
|
it "returns false" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect(result).to eq(false)
|
2013-02-06 03:16:51 +08:00
|
|
|
end
|
|
|
|
|
|
|
|
it "has not changed the user's trust level" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect(user.trust_level).to eq(TrustLevel[0])
|
2013-02-06 03:16:51 +08:00
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
context "when user has done the requisite things" do
|
2013-02-06 03:16:51 +08:00
|
|
|
before do
|
2013-10-04 11:28:49 +08:00
|
|
|
stat = user.user_stat
|
2014-09-05 04:16:46 +08:00
|
|
|
stat.topics_entered = SiteSetting.tl1_requires_topics_entered
|
|
|
|
stat.posts_read_count = SiteSetting.tl1_requires_read_posts
|
|
|
|
stat.time_read = SiteSetting.tl1_requires_time_spent_mins * 60
|
2013-02-06 03:16:51 +08:00
|
|
|
@result = promotion.review
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns true" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect(@result).to eq(true)
|
2013-02-06 03:16:51 +08:00
|
|
|
end
|
|
|
|
|
|
|
|
it "has upgraded the user to basic" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect(user.trust_level).to eq(TrustLevel[1])
|
2013-02-06 03:16:51 +08:00
|
|
|
end
|
2024-10-16 23:26:10 +08:00
|
|
|
|
|
|
|
it "allows plugins to control promotion #review" do
|
|
|
|
DiscoursePluginRegistry.register_modifier(plugin, :review_trust_level, &deny_block)
|
|
|
|
action = Promotion.new(user).review
|
|
|
|
expect(action).to eq(false)
|
|
|
|
|
|
|
|
DiscoursePluginRegistry.register_modifier(plugin, review_modifier, &allow_block)
|
|
|
|
action = Promotion.new(user).review
|
|
|
|
expect(action).to eq(true)
|
|
|
|
ensure
|
|
|
|
DiscoursePluginRegistry.unregister_modifier(plugin, review_modifier, &deny_block)
|
|
|
|
DiscoursePluginRegistry.unregister_modifier(plugin, review_modifier, &allow_block)
|
|
|
|
end
|
|
|
|
|
|
|
|
it "allows plugins to control promotion #recalculate" do
|
|
|
|
DiscoursePluginRegistry.register_modifier(plugin, recalculate_modifier, &deny_block)
|
|
|
|
action = Promotion.recalculate(user)
|
|
|
|
expect(action).to eq(nil)
|
|
|
|
|
|
|
|
DiscoursePluginRegistry.register_modifier(plugin, recalculate_modifier, &allow_block)
|
|
|
|
action = Promotion.recalculate(user)
|
|
|
|
|
|
|
|
expect(action).to eq(true)
|
|
|
|
ensure
|
|
|
|
DiscoursePluginRegistry.unregister_modifier(plugin, recalculate_modifier, &deny_block)
|
|
|
|
DiscoursePluginRegistry.unregister_modifier(plugin, recalculate_modifier, &allow_block)
|
|
|
|
end
|
2013-02-06 03:16:51 +08:00
|
|
|
end
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
context "when user has not done the requisite things" do
|
2015-04-15 00:05:09 +08:00
|
|
|
it "does not promote the user" do
|
|
|
|
user.created_at = 1.minute.ago
|
|
|
|
stat = user.user_stat
|
|
|
|
stat.topics_entered = SiteSetting.tl1_requires_topics_entered
|
|
|
|
stat.posts_read_count = SiteSetting.tl1_requires_read_posts
|
|
|
|
stat.time_read = SiteSetting.tl1_requires_time_spent_mins * 60
|
|
|
|
@result = promotion.review
|
|
|
|
expect(@result).to eq(false)
|
|
|
|
expect(user.trust_level).to eq(TrustLevel[0])
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
context "when may send tl1 promotion messages" do
|
2018-06-23 00:51:07 +08:00
|
|
|
before do
|
|
|
|
stat = user.user_stat
|
|
|
|
stat.topics_entered = SiteSetting.tl1_requires_topics_entered
|
|
|
|
stat.posts_read_count = SiteSetting.tl1_requires_read_posts
|
|
|
|
stat.time_read = SiteSetting.tl1_requires_time_spent_mins * 60
|
|
|
|
end
|
|
|
|
it "sends promotion message by default" do
|
|
|
|
SiteSetting.send_tl1_welcome_message = true
|
|
|
|
@result = promotion.review
|
2018-07-03 07:23:45 +08:00
|
|
|
expect(Jobs::SendSystemMessage.jobs.length).to eq(1)
|
|
|
|
job = Jobs::SendSystemMessage.jobs[0]
|
|
|
|
expect(job["args"][0]["user_id"]).to eq(user.id)
|
|
|
|
expect(job["args"][0]["message_type"]).to eq("welcome_tl1_user")
|
2018-06-23 00:51:07 +08:00
|
|
|
end
|
|
|
|
|
2021-05-21 09:43:47 +08:00
|
|
|
it "does not not send when the user already has the tl1 badge when recalculating" do
|
2018-09-20 03:52:45 +08:00
|
|
|
SiteSetting.send_tl1_welcome_message = true
|
|
|
|
BadgeGranter.grant(Badge.find(1), user)
|
|
|
|
stat = user.user_stat
|
|
|
|
stat.topics_entered = SiteSetting.tl1_requires_topics_entered
|
|
|
|
stat.posts_read_count = SiteSetting.tl1_requires_read_posts
|
|
|
|
stat.time_read = SiteSetting.tl1_requires_time_spent_mins * 60
|
|
|
|
Promotion.recalculate(user)
|
|
|
|
expect(Jobs::SendSystemMessage.jobs.length).to eq(0)
|
|
|
|
end
|
|
|
|
|
2021-08-11 06:39:25 +08:00
|
|
|
it "does not not send when the tl1 badge is disabled" do
|
|
|
|
SiteSetting.send_tl1_welcome_message = true
|
|
|
|
Badge.find(1).update!(enabled: false)
|
|
|
|
stat = user.user_stat
|
|
|
|
stat.topics_entered = SiteSetting.tl1_requires_topics_entered
|
|
|
|
stat.posts_read_count = SiteSetting.tl1_requires_read_posts
|
|
|
|
stat.time_read = SiteSetting.tl1_requires_time_spent_mins * 60
|
|
|
|
Promotion.recalculate(user)
|
2023-03-01 12:35:21 +08:00
|
|
|
|
|
|
|
expect(user.trust_level).to eq(1)
|
|
|
|
|
2021-08-11 06:39:25 +08:00
|
|
|
expect(Jobs::SendSystemMessage.jobs.length).to eq(0)
|
|
|
|
end
|
|
|
|
|
2023-03-01 12:35:21 +08:00
|
|
|
it "respects default trust level" do
|
|
|
|
SiteSetting.default_trust_level = 2
|
|
|
|
Promotion.recalculate(user)
|
|
|
|
expect(user.trust_level).to eq(2)
|
|
|
|
end
|
|
|
|
|
2018-06-23 00:51:07 +08:00
|
|
|
it "can be turned off" do
|
|
|
|
SiteSetting.send_tl1_welcome_message = false
|
|
|
|
@result = promotion.review
|
2018-07-03 07:23:45 +08:00
|
|
|
expect(Jobs::SendSystemMessage.jobs.length).to eq(0)
|
2018-06-23 00:51:07 +08:00
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
context "when may send tl2 promotion messages" do
|
2020-09-22 08:17:52 +08:00
|
|
|
fab!(:user) do
|
|
|
|
Fabricate(
|
|
|
|
:user,
|
|
|
|
trust_level: TrustLevel[1],
|
|
|
|
created_at: (SiteSetting.tl2_requires_time_spent_mins * 60).minutes.ago,
|
|
|
|
)
|
2023-01-09 19:18:21 +08:00
|
|
|
end
|
2020-09-22 08:17:52 +08:00
|
|
|
|
|
|
|
before do
|
|
|
|
stat = user.user_stat
|
|
|
|
stat.topics_entered = SiteSetting.tl2_requires_topics_entered
|
|
|
|
stat.posts_read_count = SiteSetting.tl2_requires_read_posts
|
|
|
|
stat.time_read = SiteSetting.tl2_requires_time_spent_mins * 60
|
|
|
|
stat.days_visited = SiteSetting.tl2_requires_days_visited
|
|
|
|
stat.likes_received = SiteSetting.tl2_requires_likes_received
|
|
|
|
stat.likes_given = SiteSetting.tl2_requires_likes_given
|
|
|
|
SiteSetting.tl2_requires_topic_reply_count = 0
|
|
|
|
SiteSetting.send_tl2_promotion_message = true
|
|
|
|
end
|
|
|
|
|
|
|
|
it "sends promotion message by default" do
|
|
|
|
expect_enqueued_with(
|
|
|
|
job: :send_system_message,
|
|
|
|
args: {
|
|
|
|
user_id: user.id,
|
|
|
|
message_type: "tl2_promotion_message",
|
|
|
|
},
|
|
|
|
) { @result = promotion.review }
|
|
|
|
end
|
|
|
|
|
|
|
|
it "can be turned off" do
|
|
|
|
SiteSetting.send_tl2_promotion_message = false
|
|
|
|
expect_not_enqueued_with(job: :send_system_message) { @result = promotion.review }
|
|
|
|
end
|
|
|
|
end
|
2013-02-06 03:16:51 +08:00
|
|
|
end
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
describe "basic" do
|
2019-05-07 11:12:20 +08:00
|
|
|
fab!(:user) { Fabricate(:user, trust_level: TrustLevel[1], created_at: 2.days.ago) }
|
2013-04-05 12:29:46 +08:00
|
|
|
let(:promotion) { Promotion.new(user) }
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
context "when has done nothing" do
|
2013-04-05 12:29:46 +08:00
|
|
|
let!(:result) { promotion.review }
|
|
|
|
|
|
|
|
it "returns false" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect(result).to eq(false)
|
2013-04-05 12:29:46 +08:00
|
|
|
end
|
|
|
|
|
|
|
|
it "has not changed the user's trust level" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect(user.trust_level).to eq(TrustLevel[1])
|
2013-04-05 12:29:46 +08:00
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
context "when has done the requisite things" do
|
2013-04-05 12:29:46 +08:00
|
|
|
before do
|
2020-05-15 06:42:00 +08:00
|
|
|
SiteSetting.tl2_requires_topic_reply_count = 3
|
|
|
|
|
2013-10-04 11:28:49 +08:00
|
|
|
stat = user.user_stat
|
2014-09-05 04:16:46 +08:00
|
|
|
stat.topics_entered = SiteSetting.tl2_requires_topics_entered
|
|
|
|
stat.posts_read_count = SiteSetting.tl2_requires_read_posts
|
|
|
|
stat.time_read = SiteSetting.tl2_requires_time_spent_mins * 60
|
|
|
|
stat.days_visited = SiteSetting.tl2_requires_days_visited * 60
|
|
|
|
stat.likes_received = SiteSetting.tl2_requires_likes_received
|
|
|
|
stat.likes_given = SiteSetting.tl2_requires_likes_given
|
2020-05-15 06:42:00 +08:00
|
|
|
SiteSetting.tl2_requires_topic_reply_count.times do |_|
|
|
|
|
topic = Fabricate(:topic)
|
|
|
|
reply = Fabricate(:post, topic: topic, user: user, post_number: 2)
|
|
|
|
end
|
2013-04-05 12:29:46 +08:00
|
|
|
|
|
|
|
@result = promotion.review
|
|
|
|
end
|
|
|
|
|
|
|
|
it "returns true" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect(@result).to eq(true)
|
2013-04-05 12:29:46 +08:00
|
|
|
end
|
|
|
|
|
|
|
|
it "has upgraded the user to regular" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect(user.trust_level).to eq(TrustLevel[2])
|
2013-04-05 12:29:46 +08:00
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2015-04-15 00:05:09 +08:00
|
|
|
context "when the account hasn't existed long enough" do
|
|
|
|
it "does not promote the user" do
|
|
|
|
user.created_at = 1.minute.ago
|
2020-05-15 06:42:00 +08:00
|
|
|
SiteSetting.tl2_requires_topic_reply_count = 3
|
2015-04-15 00:05:09 +08:00
|
|
|
|
|
|
|
stat = user.user_stat
|
|
|
|
stat.topics_entered = SiteSetting.tl2_requires_topics_entered
|
|
|
|
stat.posts_read_count = SiteSetting.tl2_requires_read_posts
|
|
|
|
stat.time_read = SiteSetting.tl2_requires_time_spent_mins * 60
|
|
|
|
stat.days_visited = SiteSetting.tl2_requires_days_visited * 60
|
|
|
|
stat.likes_received = SiteSetting.tl2_requires_likes_received
|
|
|
|
stat.likes_given = SiteSetting.tl2_requires_likes_given
|
2020-05-15 06:42:00 +08:00
|
|
|
SiteSetting.tl2_requires_topic_reply_count.times do |_|
|
|
|
|
topic = Fabricate(:topic)
|
|
|
|
reply = Fabricate(:post, topic: topic, user: user, post_number: 2)
|
|
|
|
end
|
2015-04-15 00:05:09 +08:00
|
|
|
|
|
|
|
result = promotion.review
|
|
|
|
expect(result).to eq(false)
|
|
|
|
expect(user.trust_level).to eq(TrustLevel[1])
|
|
|
|
end
|
|
|
|
end
|
2013-04-05 12:29:46 +08:00
|
|
|
end
|
2013-02-06 03:16:51 +08:00
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
describe "regular" do
|
2019-05-07 11:12:20 +08:00
|
|
|
fab!(:user) { Fabricate(:user, trust_level: TrustLevel[2]) }
|
2014-06-28 00:26:03 +08:00
|
|
|
let(:promotion) { Promotion.new(user) }
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
context "when doesn't qualify for promotion" do
|
2014-06-28 00:26:03 +08:00
|
|
|
before do
|
2014-09-05 13:20:39 +08:00
|
|
|
TrustLevel3Requirements
|
|
|
|
.any_instance
|
|
|
|
.expects(:requirements_met?)
|
|
|
|
.at_least_once
|
|
|
|
.returns(false)
|
2014-06-28 00:26:03 +08:00
|
|
|
end
|
|
|
|
|
2014-09-05 13:20:39 +08:00
|
|
|
it "review_tl2 returns false" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect { expect(promotion.review_tl2).to eq(false) }.to_not change {
|
2014-06-28 00:26:03 +08:00
|
|
|
user.reload.trust_level
|
|
|
|
}
|
|
|
|
end
|
|
|
|
|
|
|
|
it "doesn't promote" do
|
|
|
|
expect { promotion.review_tl2 }.to_not change { user.reload.trust_level }
|
|
|
|
end
|
2014-07-09 05:39:36 +08:00
|
|
|
|
|
|
|
it "doesn't log a trust level change" do
|
|
|
|
expect { promotion.review_tl2 }.to_not change { UserHistory.count }
|
|
|
|
end
|
2014-06-28 00:26:03 +08:00
|
|
|
end
|
|
|
|
|
2022-07-28 00:14:14 +08:00
|
|
|
context "when qualifies for promotion" do
|
2014-06-28 00:26:03 +08:00
|
|
|
before do
|
2014-09-05 13:20:39 +08:00
|
|
|
TrustLevel3Requirements.any_instance.expects(:requirements_met?).at_least_once.returns(true)
|
2014-06-28 00:26:03 +08:00
|
|
|
end
|
|
|
|
|
2014-09-05 13:20:39 +08:00
|
|
|
it "review_tl2 returns true" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect(promotion.review_tl2).to eq(true)
|
2014-06-28 00:26:03 +08:00
|
|
|
end
|
|
|
|
|
2014-09-05 13:20:39 +08:00
|
|
|
it "promotes to tl3" do
|
2015-01-10 00:34:37 +08:00
|
|
|
expect(promotion.review_tl2).to eq(true)
|
|
|
|
expect(user.reload.trust_level).to eq(TrustLevel[3])
|
2014-06-28 00:26:03 +08:00
|
|
|
end
|
2014-07-09 05:39:36 +08:00
|
|
|
|
|
|
|
it "logs a trust level change" do
|
2014-09-05 13:20:39 +08:00
|
|
|
expect { promotion.review_tl2 }.to change {
|
2014-07-09 05:39:36 +08:00
|
|
|
UserHistory.where(action: UserHistory.actions[:auto_trust_level_change]).count
|
|
|
|
}.by(1)
|
|
|
|
end
|
2014-06-28 00:26:03 +08:00
|
|
|
end
|
|
|
|
end
|
2023-03-30 11:52:10 +08:00
|
|
|
|
|
|
|
describe "#change_trust_level!" do
|
|
|
|
fab!(:user) { Fabricate(:user, trust_level: TrustLevel[0]) }
|
|
|
|
let(:promotion) { Promotion.new(user) }
|
|
|
|
|
|
|
|
context "when the user has no emails" do
|
|
|
|
before { user.user_emails.delete_all }
|
|
|
|
|
|
|
|
it "does not error" do
|
|
|
|
expect { promotion.change_trust_level!(TrustLevel[1]) }.not_to raise_error
|
|
|
|
expect(user.reload.trust_level).to eq(TrustLevel[1])
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
2013-02-06 03:16:51 +08:00
|
|
|
end
|