From ad78c7b71a1543774a3abdf34dfc32c7376fb74a Mon Sep 17 00:00:00 2001 From: mbernier Date: Sun, 1 Oct 2017 12:29:15 -0600 Subject: [PATCH 1/6] Allows users to submit rfc822 formatted email addresses Closes #277 --- sendgrid/helpers/mail/mail.py | 32 +++++++++++++++++++++++++------- 1 file changed, 25 insertions(+), 7 deletions(-) diff --git a/sendgrid/helpers/mail/mail.py b/sendgrid/helpers/mail/mail.py index de41bad70..6cecd66a1 100644 --- a/sendgrid/helpers/mail/mail.py +++ b/sendgrid/helpers/mail/mail.py @@ -260,13 +260,15 @@ def add_custom_arg(self, custom_arg): class Email(object): def __init__(self, email=None, name=None): - self._name = None - self._email = None - - if email is not None: - self.email = email - if name is not None: - self.name = name + if not name + # allows passing emails as "dude Fella " + self.parse_email(email) + else: + #allows backwards compatibility for Email(email, name) + if email is not None: + self.email = email + if name is not None: + self.name = name @property def name(self): @@ -293,6 +295,22 @@ def get(self): email["email"] = self.email return email + def parse_email(self, email_info): + try: + import rfc822 + except ImportError: + import email.utils as rfc822 + + name, email = rfc822.parseaddr(email_info) + if not name: + name = None + + if not email: + email = None + + self.name(name) + self.email(email) + return name, email class Content(object): From fd2e28f1fbf749aba044396e9f5bdc1831fc7fb0 Mon Sep 17 00:00:00 2001 From: mbernier Date: Mon, 2 Oct 2017 10:08:32 -0600 Subject: [PATCH 2/6] updated to fix the bug --- sendgrid/helpers/mail/mail.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/sendgrid/helpers/mail/mail.py b/sendgrid/helpers/mail/mail.py index 6cecd66a1..cf6312656 100644 --- a/sendgrid/helpers/mail/mail.py +++ b/sendgrid/helpers/mail/mail.py @@ -265,9 +265,9 @@ def __init__(self, email=None, name=None): self.parse_email(email) else: #allows backwards compatibility for Email(email, name) - if email is not None: + if not email: self.email = email - if name is not None: + if not name: self.name = name @property From 8d24621398ae4407f0bf4833fe6c2c9b279a58de Mon Sep 17 00:00:00 2001 From: mbernier Date: Mon, 2 Oct 2017 10:12:24 -0600 Subject: [PATCH 3/6] missing a colon - Also realized, we already checked that name exists... so we don't have to check again --- sendgrid/helpers/mail/mail.py | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/sendgrid/helpers/mail/mail.py b/sendgrid/helpers/mail/mail.py index cf6312656..24e56a9f8 100644 --- a/sendgrid/helpers/mail/mail.py +++ b/sendgrid/helpers/mail/mail.py @@ -260,15 +260,14 @@ def add_custom_arg(self, custom_arg): class Email(object): def __init__(self, email=None, name=None): - if not name + if not name: # allows passing emails as "dude Fella " self.parse_email(email) else: #allows backwards compatibility for Email(email, name) - if not email: + if email is not None: self.email = email - if not name: - self.name = name + self.name = name @property def name(self): From 84d81bb6d7711ec9ae45133197836795850f3e78 Mon Sep 17 00:00:00 2001 From: mbernier Date: Tue, 3 Oct 2017 08:17:35 -0600 Subject: [PATCH 4/6] Changed all access methods to use get/set, initialize name/email The class was not using get/set methods for all calls. As well, email and name were not initialized. This is now rectified. --- sendgrid/helpers/mail/mail.py | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/sendgrid/helpers/mail/mail.py b/sendgrid/helpers/mail/mail.py index 24e56a9f8..767f60ae0 100644 --- a/sendgrid/helpers/mail/mail.py +++ b/sendgrid/helpers/mail/mail.py @@ -260,14 +260,16 @@ def add_custom_arg(self, custom_arg): class Email(object): def __init__(self, email=None, name=None): + self._name(None) + self._email(None) if not name: # allows passing emails as "dude Fella " self.parse_email(email) else: #allows backwards compatibility for Email(email, name) if email is not None: - self.email = email - self.name = name + self.email(email) + self.name(name) @property def name(self): @@ -287,11 +289,11 @@ def email(self, value): def get(self): email = {} - if self.name is not None: - email["name"] = self.name + if self.name() is not None: + email["name"] = self.name() - if self.email is not None: - email["email"] = self.email + if self.email() is not None: + email["email"] = self.email() return email def parse_email(self, email_info): From 86abbc199800fefe9114cab7535d28a8114cca78 Mon Sep 17 00:00:00 2001 From: mbernier Date: Sun, 22 Oct 2017 11:28:07 -0600 Subject: [PATCH 5/6] Updated to fix teh NoneType errors --- sendgrid/helpers/mail/mail.py | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/sendgrid/helpers/mail/mail.py b/sendgrid/helpers/mail/mail.py index 767f60ae0..f9d48397a 100644 --- a/sendgrid/helpers/mail/mail.py +++ b/sendgrid/helpers/mail/mail.py @@ -260,16 +260,16 @@ def add_custom_arg(self, custom_arg): class Email(object): def __init__(self, email=None, name=None): - self._name(None) - self._email(None) + self._name = None + self._email = None if not name: # allows passing emails as "dude Fella " self.parse_email(email) else: #allows backwards compatibility for Email(email, name) if email is not None: - self.email(email) - self.name(name) + self.email = email + self.name = name @property def name(self): @@ -289,11 +289,11 @@ def email(self, value): def get(self): email = {} - if self.name() is not None: - email["name"] = self.name() + if self.name is not None: + email["name"] = self.name - if self.email() is not None: - email["email"] = self.email() + if self.email is not None: + email["email"] = self.email return email def parse_email(self, email_info): @@ -309,8 +309,8 @@ def parse_email(self, email_info): if not email: email = None - self.name(name) - self.email(email) + self.name = name + self.email = email return name, email class Content(object): From 3f876afbd4732441b60d0b0b577f1c1a3c7ab45d Mon Sep 17 00:00:00 2001 From: mbernier Date: Mon, 23 Oct 2017 15:58:00 -0600 Subject: [PATCH 6/6] added unittests and updated Email class email class now allows empty instantiation without error If a name is passed, i.e. an email with no '@', then the name gets set rather than defaulting to email param --- sendgrid/helpers/mail/mail.py | 23 +++++++++----- test/test_email.py | 59 +++++++++++++++++++++++++++++++++++ 2 files changed, 74 insertions(+), 8 deletions(-) create mode 100644 test/test_email.py diff --git a/sendgrid/helpers/mail/mail.py b/sendgrid/helpers/mail/mail.py index f9d48397a..a2159b25d 100644 --- a/sendgrid/helpers/mail/mail.py +++ b/sendgrid/helpers/mail/mail.py @@ -262,14 +262,15 @@ class Email(object): def __init__(self, email=None, name=None): self._name = None self._email = None - if not name: - # allows passing emails as "dude Fella " - self.parse_email(email) - else: - #allows backwards compatibility for Email(email, name) - if email is not None: - self.email = email - self.name = name + if name or email: + if not name: + # allows passing emails as "dude Fella " + self.parse_email(email) + else: + #allows backwards compatibility for Email(email, name) + if email is not None: + self.email = email + self.name = name @property def name(self): @@ -303,6 +304,12 @@ def parse_email(self, email_info): import email.utils as rfc822 name, email = rfc822.parseaddr(email_info) + + # more than likely a string was passed here instead of an email address + if "@" not in email: + name = email + email = None + if not name: name = None diff --git a/test/test_email.py b/test/test_email.py new file mode 100644 index 000000000..92ae10aaa --- /dev/null +++ b/test/test_email.py @@ -0,0 +1,59 @@ +# -*- coding: utf-8 -*- +import json + +from sendgrid.helpers.mail import (Email) + +try: + import unittest2 as unittest +except ImportError: + import unittest + + +class TestEmailObject(unittest.TestCase): + def test_add_email_address(self): + address = "test@example.com" + email = Email(address) + + self.assertEqual(email.email, "test@example.com") + + def test_add_name(self): + name = "SomeName" + email = Email(name=name) + + self.assertEqual(email.name, name) + + def test_add_name_email(self): + name = "SomeName" + address = "test@example.com" + email = Email(email=address, name=name) + self.assertEqual(email.name, name) + self.assertEqual(email.email, "test@example.com") + + def test_add_rfc_function_finds_name_not_email(self): + name = "SomeName" + email = Email(name) + + self.assertEqual(email.name, name) + self.assertIsNone(email.email) + + def test_add_rfc_email(self): + name = "SomeName" + address = "test@example.com" + name_address = "{0} <{1}>".format(name, address) + email = Email(name_address) + self.assertEqual(email.name, name) + self.assertEqual(email.email, "test@example.com") + + def test_empty_obj_add_name(self): + email = Email() + name = "SomeName" + email.name = name + + self.assertEqual(email.name, name) + + def test_empty_obj_add_email(self): + email = Email() + address = "test@example.com" + email.email = address + + self.assertEqual(email.email, address) \ No newline at end of file