FEATURE: Use group SMTP job and mailer instead of UserNotifications change (#13489)

This PR backtracks a fair bit on this one https://github.com/discourse/discourse/pull/13220/files.

Instead of sending the group SMTP email for each user via `UserNotifications`, we are changing to send only one email with the existing `Jobs::GroupSmtpEmail` job and `GroupSmtpMailer`. We are changing this job and mailer along with `PostAlerter` to make the first topic allowed user the `to_address` for the email and any other `topic_allowed_users` to be the CC address on the email. This is to cut down on emails sent via SMTP, which is subject to daily limits from providers such as Gmail. We log these details in the `EmailLog` table now.

In addition to this, we have changed `PostAlerter` to no longer rely on incoming email email addresses for sending the `GroupSmtpEmail` job. This was unreliable as a user's email could have changed in the meantime. Also it was a little overcomplicated to use the incoming email records -- it is far simpler to reason about to just use topic allowed users.

This also adds a fix to include cc_addresses in the EmailLog.addressed_to_user scope.
This commit is contained in:
Martin Brennan
2021-06-28 08:55:13 +10:00
committed by GitHub
parent f9886ecfa2
commit 87684f7c5e
14 changed files with 484 additions and 284 deletions

View File

@ -152,12 +152,15 @@ describe Email::MessageBuilder do
context "header args" do
let(:additional_opts) { {} }
let(:message_with_header_args) do
Email::MessageBuilder.new(
to_address,
{
body: 'hello world',
topic_id: 1234,
post_id: 4567,
}.merge(additional_opts)
)
end
@ -169,6 +172,42 @@ describe Email::MessageBuilder do
expect(message_with_header_args.header_args['X-Discourse-Topic-Id']).to eq('1234')
end
it "uses the default reply-to header" do
expect(message_with_header_args.header_args['Reply-To']).to eq("\"Discourse\" <#{SiteSetting.notification_email}>")
end
context "when allow_reply_by_email is enabled " do
let(:additional_opts) { { allow_reply_by_email: true } }
it "uses the reply by email address if that is enabled" do
SiteSetting.manual_polling_enabled = true
SiteSetting.reply_by_email_address = "test+%{reply_key}@test.com"
SiteSetting.reply_by_email_enabled = true
expect(message_with_header_args.header_args['Reply-To']).to eq("\"Discourse\" <test+%{reply_key}@test.com>")
end
end
context "when allow_reply_by_email is enabled and use_from_address_for_reply_to is enabled but no from address is specified" do
let(:additional_opts) { { allow_reply_by_email: true, use_from_address_for_reply_to: true } }
it "uses the notification_email address, the default reply-to header" do
SiteSetting.manual_polling_enabled = true
SiteSetting.reply_by_email_address = "test+%{reply_key}@test.com"
SiteSetting.reply_by_email_enabled = true
expect(message_with_header_args.header_args['Reply-To']).to eq("\"Discourse\" <#{SiteSetting.notification_email}>")
end
end
context "when allow_reply_by_email is enabled and use_from_address_for_reply_to is enabled and from is specified" do
let(:additional_opts) { { allow_reply_by_email: true, use_from_address_for_reply_to: true, from: "team@test.com" } }
it "removes the reply-to header because it is identical to the from header" do
SiteSetting.manual_polling_enabled = true
SiteSetting.reply_by_email_address = "test+%{reply_key}@test.com"
SiteSetting.reply_by_email_enabled = true
expect(message_with_header_args.header_args['Reply-To']).to eq(nil)
end
end
end
context "unsubscribe link" do
@ -337,7 +376,5 @@ describe Email::MessageBuilder do
SiteSetting.stubs(:email_site_title).returns("::>>>Best \"Forum\", EU: Award Winning<<<")
expect(build_args[:from]).to eq("\"Best Forum EU Award Winning\" <#{SiteSetting.notification_email}>")
end
end
end

View File

@ -343,11 +343,10 @@ describe Email::Sender do
let(:reply) { Fabricate(:post, topic: post.topic, reply_to_user: post.user, reply_to_post_number: post.post_number) }
let(:notification) { Fabricate(:posted_notification, user: post.user, post: reply) }
let(:message) do
UserNotifications.user_private_message(
post.user,
post: reply,
notification_type: notification.notification_type,
notification_data_hash: notification.data_hash
GroupSmtpMailer.send_mail(
group,
post.user.email,
post
)
end
let(:group) { Fabricate(:smtp_group) }