@@ -649,6 +649,106 @@ to "/contact/thanks/" when it's done::
649649
650650.. _Header injection: http://www.nyphp.org/phundamentals/8_Preventing-Email-Header-Injection.html
651651
652+ .. _topics-sending-multiple-emails:
653+
654+ Sending many messages efficiently
655+ ---------------------------------
656+
657+ Establishing and closing an SMTP connection (or any other network connection,
658+ for that matter) is an expensive process. If you have a lot of emails to send,
659+ it makes sense to reuse an SMTP connection, rather than creating and
660+ destroying a connection every time you want to send an email.
661+
662+ There are two ways to tell an email backend to reuse a connection. Both
663+ require an email backend instance obtained via :func:`get_connection`, which is
664+ documented in :ref:`topic-email-backends`.
665+
666+ The first approach is to obtain an email backend instance from
667+ :func:`get_connection` and use its ``send_messages()`` method. This takes a
668+ list of :class:`EmailMessage` (or subclass) instances, and sends them all using
669+ that single connection. As a consequence, any :class:`connection
670+ <EmailMessage>` set on an individual message is ignored.
671+
672+ For example, if you have a function called ``get_notification_emails()`` that
673+ returns a list of :class:`EmailMessage` objects representing some periodic
674+ email you wish to send out, you could send these emails using a single call to
675+ ``send_messages()``::
676+
677+ from django.core import mail
678+
679+ connection = mail.get_connection() # Use default email connection
680+ messages = get_notification_emails()
681+ connection.send_messages(messages)
682+
683+ In this example, the call to ``send_messages()`` opens a connection on the
684+ backend, sends the list of messages, and then closes the connection again.
685+
686+ The second approach is to use the ``open()`` and ``close()`` methods on the
687+ email backend to manually control the connection. ``send_messages()`` will not
688+ open or close the connection if it is already open, so if you
689+ manually open the connection, you can control when it is closed. For example::
690+
691+ from django.core import mail
692+
693+ connection = mail.get_connection()
694+
695+ # Manually open the connection.
696+ connection.open()
697+
698+ # Construct an email message that will use the connection.
699+ email1 = mail.EmailMessage(
700+ "Hello",
701+ "Body goes here",
702+ "from@example.com",
703+ ["to1@example.com"],
704+ connection=connection,
705+ )
706+ # Send the email through its connection. The connection was already open,
707+ # so send() leaves it open after sending.
708+ email1.send()
709+
710+ # Construct two more email messages. (Passing None as the third argument
711+ # uses settings.DEFAULT_FROM_EMAIL as the "From:" address.)
712+ email2 = mail.EmailMessage("Hi", "Message", None, ["to2@example.com"])
713+ email3 = mail.EmailMessage("Hi", "Message", None, ["to3@example.com"])
714+ # Send the two messages. The connection is still open.
715+ connection.send_messages([email2, email3])
716+
717+ # Because we opened it, we need to manually close the connection.
718+ connection.close()
719+
720+ When you manually open a backend's connection, you are responsible for ensuring
721+ it gets closed. The example above actually has a bug: if an exception occurs
722+ while sending the messages, the connection will not be closed. You could fix
723+ this with a try-finally statement. Or it's often more convenient to use the
724+ backend instance as a context manager, which will automatically call ``open()``
725+ and ``close()`` as needed.
726+
727+ This is equivalent to the previous example, but uses the backend as a
728+ :ref:`context manager <context-managers>` to avoid leaving the connection open
729+ on errors::
730+
731+ from django.core import mail
732+
733+ with mail.get_connection() as connection:
734+ # The backend connection is automatically opened inside the context.
735+ email1 = mail.EmailMessage(
736+ "Hello",
737+ "Body goes here",
738+ "from@example.com",
739+ ["to1@example.com"],
740+ connection=connection,
741+ )
742+ email1.send()
743+
744+ # The connection is still open, and is reused for the second send.
745+ email2 = mail.EmailMessage("Hi", "Message", None, ["to2@example.com"])
746+ email3 = mail.EmailMessage("Hi", "Message", None, ["to3@example.com"])
747+ connection.send_messages([email2, email3])
748+
749+ # After exiting the context (either normally or because of an error),
750+ # the backend connection is automatically closed.
751+
652752.. _topic-email-backends:
653753
654754Email backends
@@ -668,25 +768,8 @@ The email backend class has the following methods:
668768 open, it will be left open after mail has been sent.
669769
670770It can also be used as a context manager, which will automatically call
671- ``open()`` and ``close()`` as needed::
672-
673- from django.core import mail
674-
675- with mail.get_connection() as connection:
676- mail.EmailMessage(
677- subject1,
678- body1,
679- from1,
680- [to1],
681- connection=connection,
682- ).send()
683- mail.EmailMessage(
684- subject2,
685- body2,
686- from2,
687- [to2],
688- connection=connection,
689- ).send()
771+ ``open()`` and ``close()`` as needed. An example is in
772+ :ref:`topics-sending-multiple-emails`.
690773
691774Django ships with several email sending backends. With the exception of the
692775SMTP backend (which is the default), these backends are only useful during
@@ -844,80 +927,6 @@ email backend.
844927
845928 Passing ``fail_silently`` as positional argument is deprecated.
846929
847- .. _topics-sending-multiple-emails:
848-
849- Sending multiple emails
850- -----------------------
851-
852- Establishing and closing an SMTP connection (or any other network connection,
853- for that matter) is an expensive process. If you have a lot of emails to send,
854- it makes sense to reuse an SMTP connection, rather than creating and
855- destroying a connection every time you want to send an email.
856-
857- There are two ways you tell an email backend to reuse a connection.
858-
859- Firstly, you can use the ``send_messages()`` method on a connection. This takes
860- a list of :class:`EmailMessage` (or subclass) instances, and sends them all
861- using that single connection. As a consequence, any :class:`connection
862- <EmailMessage>` set on an individual message is ignored.
863-
864- For example, if you have a function called ``get_notification_email()`` that
865- returns a list of :class:`EmailMessage` objects representing some periodic
866- email you wish to send out, you could send these emails using a single call to
867- ``send_messages()``::
868-
869- from django.core import mail
870-
871- connection = mail.get_connection() # Use default email connection
872- messages = get_notification_email()
873- connection.send_messages(messages)
874-
875- In this example, the call to ``send_messages()`` opens a connection on the
876- backend, sends the list of messages, and then closes the connection again.
877-
878- The second approach is to use the ``open()`` and ``close()`` methods on the
879- email backend to manually control the connection. ``send_messages()`` will not
880- manually open or close the connection if it is already open, so if you
881- manually open the connection, you can control when it is closed. For example::
882-
883- from django.core import mail
884-
885- connection = mail.get_connection()
886-
887- # Manually open the connection
888- connection.open()
889-
890- # Construct an email message that uses the connection
891- email1 = mail.EmailMessage(
892- "Hello",
893- "Body goes here",
894- "from@example.com",
895- ["to1@example.com"],
896- connection=connection,
897- )
898- email1.send() # Send the email
899-
900- # Construct two more messages
901- email2 = mail.EmailMessage(
902- "Hello",
903- "Body goes here",
904- "from@example.com",
905- ["to2@example.com"],
906- )
907- email3 = mail.EmailMessage(
908- "Hello",
909- "Body goes here",
910- "from@example.com",
911- ["to3@example.com"],
912- )
913-
914- # Send the two emails in a single call.
915- connection.send_messages([email2, email3])
916- # The connection was already open so send_messages() doesn't close it.
917- # We need to manually close the connection.
918- connection.close()
919-
920-
921930Configuring email for development
922931=================================
923932
0 commit comments