-
Notifications
You must be signed in to change notification settings - Fork 715
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: add support for Twilio Email (#882)
- Loading branch information
childish-sambino
authored
Apr 21, 2020
1 parent
83b28b8
commit 1adc410
Showing
10 changed files
with
273 additions
and
107 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,62 @@ | ||
import python_http_client | ||
|
||
|
||
class BaseInterface(object): | ||
def __init__(self, auth, host, impersonate_subuser): | ||
""" | ||
Construct the Twilio SendGrid v3 API object. | ||
Note that the underlying client is being set up during initialization, | ||
therefore changing attributes in runtime will not affect HTTP client | ||
behaviour. | ||
:param auth: the authorization header | ||
:type auth: string | ||
:param impersonate_subuser: the subuser to impersonate. Will be passed | ||
by "On-Behalf-Of" header by underlying | ||
client. See | ||
https://sendgrid.com/docs/User_Guide/Settings/subusers.html | ||
for more details | ||
:type impersonate_subuser: string | ||
:param host: base URL for API calls | ||
:type host: string | ||
""" | ||
from . import __version__ | ||
self.auth = auth | ||
self.host = host | ||
self.impersonate_subuser = impersonate_subuser | ||
self.version = __version__ | ||
self.useragent = 'sendgrid/{};python'.format(self.version) | ||
|
||
self.client = python_http_client.Client( | ||
host=self.host, | ||
request_headers=self._default_headers, | ||
version=3) | ||
|
||
@property | ||
def _default_headers(self): | ||
"""Set the default header for a Twilio SendGrid v3 API call""" | ||
headers = { | ||
"Authorization": self.auth, | ||
"User-Agent": self.useragent, | ||
"Accept": 'application/json' | ||
} | ||
if self.impersonate_subuser: | ||
headers['On-Behalf-Of'] = self.impersonate_subuser | ||
|
||
return headers | ||
|
||
def reset_request_headers(self): | ||
self.client.request_headers = self._default_headers | ||
|
||
def send(self, message): | ||
"""Make a Twilio SendGrid v3 API request with the request body generated by | ||
the Mail object | ||
:param message: The Twilio SendGrid v3 API request body generated by the Mail | ||
object | ||
:type message: Mail | ||
""" | ||
if not isinstance(message, dict): | ||
message = message.get() | ||
|
||
return self.client.mail.send.post(request_body=message) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,73 @@ | ||
""" | ||
This library allows you to quickly and easily use the Twilio Email Web API v3 via Python. | ||
For more information on this library, see the README on GitHub. | ||
http://github.com/sendgrid/sendgrid-python | ||
For more information on the Twilio SendGrid v3 API, see the v3 docs: | ||
http://sendgrid.com/docs/API_Reference/api_v3.html | ||
For the user guide, code examples, and more, visit the main docs page: | ||
http://sendgrid.com/docs/index.html | ||
This file provides the Twilio Email API Client. | ||
""" | ||
import os | ||
from base64 import b64encode | ||
|
||
from .base_interface import BaseInterface | ||
|
||
|
||
class TwilioEmailAPIClient(BaseInterface): | ||
"""The Twilio Email API Client. | ||
Use this object to interact with the v3 API. For example: | ||
mail_client = sendgrid.TwilioEmailAPIClient(os.environ.get('TWILIO_API_KEY'), | ||
os.environ.get('TWILIO_API_SECRET')) | ||
... | ||
mail = Mail(from_email, subject, to_email, content) | ||
response = mail_client.send(mail) | ||
For examples and detailed use instructions, see | ||
https://github.com/sendgrid/sendgrid-python | ||
""" | ||
|
||
def __init__( | ||
self, | ||
username=None, | ||
password=None, | ||
host='https://email.twilio.com', | ||
impersonate_subuser=None): | ||
""" | ||
Construct the Twilio Email v3 API object. | ||
Note that the underlying client is being set up during initialization, | ||
therefore changing attributes in runtime will not affect HTTP client | ||
behaviour. | ||
:param username: Twilio Email API key SID or Account SID to use. If not | ||
provided, value will be read from the environment | ||
variable "TWILIO_API_KEY" or "TWILIO_ACCOUNT_SID" | ||
:type username: string | ||
:param password: Twilio Email API key secret or Account Auth Token to | ||
use. If not provided, value will be read from the | ||
environment variable "TWILIO_API_SECRET" or | ||
"TWILIO_AUTH_TOKEN" | ||
:type password: string | ||
:param impersonate_subuser: the subuser to impersonate. Will be passed | ||
by "On-Behalf-Of" header by underlying | ||
client. See | ||
https://sendgrid.com/docs/User_Guide/Settings/subusers.html | ||
for more details | ||
:type impersonate_subuser: string | ||
:param host: base URL for API calls | ||
:type host: string | ||
""" | ||
self.username = username or \ | ||
os.environ.get('TWILIO_API_KEY') or \ | ||
os.environ.get('TWILIO_ACCOUNT_SID') | ||
|
||
self.password = password or \ | ||
os.environ.get('TWILIO_API_SECRET') or \ | ||
os.environ.get('TWILIO_AUTH_TOKEN') | ||
|
||
auth = 'Basic ' + b64encode('{}:{}'.format(self.username, self.password).encode()).decode() | ||
|
||
super(TwilioEmailAPIClient, self).__init__(auth, host, impersonate_subuser) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,37 @@ | ||
import os | ||
import unittest | ||
|
||
from sendgrid import TwilioEmailAPIClient | ||
|
||
|
||
class UnitTests(unittest.TestCase): | ||
|
||
@classmethod | ||
def setUpClass(cls): | ||
os.environ['TWILIO_API_KEY'] = 'api-key' | ||
os.environ['TWILIO_API_SECRET'] = 'api-secret' | ||
os.environ['TWILIO_ACCOUNT_SID'] = 'account-sid' | ||
os.environ['TWILIO_AUTH_TOKEN'] = 'auth-token' | ||
|
||
def test_init_key_over_token(self): | ||
mail_client = TwilioEmailAPIClient() | ||
|
||
self.assertEqual(mail_client.username, 'api-key') | ||
self.assertEqual(mail_client.password, 'api-secret') | ||
self.assertEqual(mail_client.host, 'https://email.twilio.com') | ||
|
||
def test_init_token(self): | ||
del os.environ['TWILIO_API_KEY'] | ||
del os.environ['TWILIO_API_SECRET'] | ||
|
||
mail_client = TwilioEmailAPIClient() | ||
|
||
self.assertEqual(mail_client.username, 'account-sid') | ||
self.assertEqual(mail_client.password, 'auth-token') | ||
|
||
def test_init_args(self): | ||
mail_client = TwilioEmailAPIClient('username', 'password') | ||
|
||
self.assertEqual(mail_client.username, 'username') | ||
self.assertEqual(mail_client.password, 'password') | ||
self.assertEqual(mail_client.auth, 'Basic dXNlcm5hbWU6cGFzc3dvcmQ=') |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.