【问题标题】:How to make send_mail function send bcc emails - Django REST API如何使 send_mail 函数发送密件抄送电子邮件 - Django REST API
【发布时间】:2021-05-15 14:36:29
【问题描述】:

如果聊天中有新消息,我想向聊天中的所有人(消息作者除外)发送通知。我想向所有人发送一封电子邮件,这样没有人可以看到其他人的电子邮件地址(密件抄送)。我该怎么做?

这是我的看法:

class WriteMessageCreateAPIView(generics.CreateAPIView):
    permission_classes = [IsAuthenticated, IsParticipant]
    serializer_class = MessageSerializer

def perform_create(self, serializer):
    ...
    chat = serializer.validated_data['chat']
    chat_recipients = chat.participants.exclude(id=self.request.user.id)

    for participant in chat_recipients:
        MessageRecipient.objects.create(message_id=new_message.id, recipient_id=participant.id)

    send_new_message_notification(chat.id, new_message.author, chat_recipients)

这里会同时向所有收件人发送一封电子邮件,但采用抄送形式(每个人都可以看到彼此的电子邮件地址)。

这里是 send_mail 函数:

def send_new_message_notification(chat_id, sender: User, recipients):
    link = BASE_URL + '/messaging/chat/%s/messages' % chat_id
    send_email(
        subject='You have a new message',
        message='Click the link below to view the message:', link),
        from_email='some_email@email.com',
        recipient_list=recipients
)

是的,我可以在视图部分这样做:

for participant in chat_recipients:
        MessageRecipient.objects.create(message_id=new_message.id, recipient_id=participant.id)
        send_new_message_notification(chat.id, new_message.author, participant)

并且一个一个发送,但是效率不高。

所以问题是:有什么方法可以同时向所有收件人发送电子邮件,这样他们就无法看到彼此的电子邮件地址?

【问题讨论】:

    标签: django email django-rest-framework


    【解决方案1】:

    是的。 Django 有一个 send_mass_mail 函数正是为了这个目的。您可以查看文档here。

    # This is more efficient, because it hits the database only
    # once instead of once for each new MessageRecipient
    message_recipients = [MessageRecipient(message_id=new_message.id, recipient_id=participant.id) for participant in chat_recipients]
    MessageRecipient.objects.bulk_create(message_recipients)
    
    # This will send separate emails, but will only make
    # one connection with the email server so it will be
    # more efficient
    link = BASE_URL + '/messaging/chat/%s/messages' % chat.id
    emails = (('You have a new message',
               f'Click the link below to view the message: {link}', 
               'some_email@email.com',
               [recepient]
               ) for recepient in chat_recepients)
    send_mass_mail(emails, fail_silently=False)
    
    

    【讨论】:

    • 感谢您重构 MessageRecipient 实例的创建。我把它改写为你的版本。邮箱呢,可惜没解决问题,通知来的时候还能看到其他收件人的邮箱……估计是邮件不是单独发送的。
    • 哦,似乎不可能使用 send_mass_mail 隐藏收件人的电子邮件地址,正如 django 文档中所说:与 send_mail() 一样,同一收件人列表中的收件人将所有人都可以在电子邮件的“收件人:”字段中看到其他地址。
    • @mahiraa 在 django 文档中通知它说“同一收件人列表中的收件人”。此处的收件人位于单独的收件人列表中。这应该发送单独的电子邮件。所以这不是密件抄送,但收件人应该看不到其他收件人的电子邮件。
    • 是的,你是对的。我按照你说的写了:```link = BASE_URL + '/messaging/chat/%s/messages' % chat_id emails = (('你有一条新消息', '{} {}给你发了一条新消息。点击以下链接可查看邮件:\n\n{}'.format(sender.first_name, sender.last_name, link), 'some_email@email.com', recipient) for recipients in recipients) send_mass_mail(emails, fail_silently= False)```,这是最后一个错误:'User' object is not iterable。你不知道如何解决它吗?
    • 很可能您使用的变量recipients 指的是单个用户,而不是收件人列表,您的意思是改用chat_recipients 吗? (你有for recipient in recipients)
    猜你喜欢
    • 2013-06-08
    • 2012-03-20
    • 1970-01-01
    • 1970-01-01
    • 2020-08-09
    • 1970-01-01
    • 2020-10-10
    • 1970-01-01
    相关资源
    最近更新 更多