How to send an email from backend?
In the ShipFast.dev, you can send emails from the backend by creating a new class that subclasses the Email
class.
The Email
class is a base class that provides common functionality for sending emails.
This guide assumes that you are already familiar with async workers and Django REST Framework (DRF) serializers. If you are not familiar with these concepts, we recommend that you read the following articles:
Email Serializer
In the ShipFast.dev, email data is serialized using the Django REST Framework serializers. Serializers define how data should be converted to and from JSON format, making it easy to transmit data over the Amazon EventBridge API.
Here's an example of an email serializer used in the ShipFast.dev:
from rest_framework import serializers
class AccountActivationEmailSerializer(serializers.Serializer):
user_id = serializers.CharField()
token = serializers.CharField()
In this example, the AccountActivationEmailSerializer
defines two fields - user_id
and token
- that are used to serialize email data for the account activation email.
When an email is sent, the email data is first validated using the serializer to ensure that it contains the required fields and that the data is in the expected format. Once validated, the serializer is used to convert the email data to JSON format, which can then be transmitted over the API.
Email Class and Sending Emails
To create a new email class, you can subclass the common.emails.Email
class and define the necessary properties and methods.
In the ShipFast.dev, the Email
class is a subclass of the common.tasks.Task
class, which emits the email event to be handled by async workers.
The email handler then uses the AWS SES to send the email.
For example, the following code defines a new email class that sends the account activation email:
from common import emails
from . import email_serializers
class UserEmail(emails.Email):
def __init__(self, user, data=None):
super().__init__(to=user.email, data=data)
class AccountActivationEmail(UserEmail):
name = 'ACCOUNT_ACTIVATION'
serializer_class = email_serializers.AccountActivationEmailSerializer
In this example, the UserEmail
class is defined as a subclass of the Email
class.
It takes a user
argument and automatically sets the email recipient to the user's email address.
The AccountActivationEmail
class then subclasses the UserEmail
class and specifies the name of the email as 'ACCOUNT_ACTIVATION'
, along with the serializer class to use for serializing the email data.
To send an activation email, you can simply invoke the AccountActivationEmail
class and call the send()
method with the required parameters.
from django.contrib import auth as dj_auth
from django.contrib.auth.models import update_last_login
from rest_framework import serializers
from rest_framework_simplejwt import tokens as jwt_tokens
from rest_framework_simplejwt.settings import api_settings as jwt_api_settings
from . import tokens, notifications
class UserSignupSerializer(serializers.ModelSerializer):
# ...
def create(self, validated_data):
user = dj_auth.get_user_model().objects.create_user(
validated_data["email"],
validated_data["password"],
)
refresh = jwt_tokens.RefreshToken.for_user(user)
if jwt_api_settings.UPDATE_LAST_LOGIN:
update_last_login(None, user)
notifications.AccountActivationEmail(
user=user, data={'user_id': user.id.hashid, 'token': tokens.account_activation_token.make_token(user)}
).send()
return {'id': user.id, 'email': user.email, 'access': str(refresh.access_token), 'refresh': str(refresh)}