From bedeb56759a337d4dfb5c572fe9f7666d5e940fb Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Alexandre=20D=C3=ADaz?=
Date: Thu, 19 Mar 2020 20:30:34 +0100
Subject: [PATCH] [IMP] mail_tracking: Store To recipients and omit aliases
---
mail_tracking/README.rst | 5 ++
mail_tracking/models/__init__.py | 1 +
mail_tracking/models/mail_alias.py | 33 ++++++++++
mail_tracking/models/mail_message.py | 59 +++++++++++++-----
mail_tracking/models/mail_thread.py | 51 ++++++++-------
mail_tracking/readme/USAGE.rst | 5 ++
mail_tracking/static/description/index.html | 1 +
mail_tracking/static/src/img/anon_user.png | Bin 0 -> 483 bytes
.../static/src/xml/mail_tracking.xml | 5 ++
mail_tracking/tests/test_mail_tracking.py | 5 +-
10 files changed, 126 insertions(+), 39 deletions(-)
create mode 100644 mail_tracking/models/mail_alias.py
create mode 100644 mail_tracking/static/src/img/anon_user.png
diff --git a/mail_tracking/README.rst b/mail_tracking/README.rst
index aaf3574..d37ee6b 100644
--- a/mail_tracking/README.rst
+++ b/mail_tracking/README.rst
@@ -76,6 +76,9 @@ These are all available status icons:
.. |noemail| image:: https://raw.githubusercontent.com/OCA/social/13.0/mail_tracking/static/src/img/no_email.png
:width: 10px
+.. |anonuser| image:: https://raw.githubusercontent.com/OCA/social/13.0/mail_tracking/static/src/img/anon_user.png
+ :width: 10px
+
|unknown| **Unknown**: No email tracking info available. Maybe this notified partner has 'Receive Inbox Notifications by Email' == 'Never'
|waiting| **Waiting**: Waiting to be sent
@@ -92,6 +95,8 @@ These are all available status icons:
|noemail| **No Email**: The partner doesn't have a defined email
+|anonuser| **No Partner**: The recipient doesn't have a defined partner
+
If you want to see all tracking emails and events you can go to
diff --git a/mail_tracking/models/__init__.py b/mail_tracking/models/__init__.py
index 896721a..0f2e248 100644
--- a/mail_tracking/models/__init__.py
+++ b/mail_tracking/models/__init__.py
@@ -9,3 +9,4 @@ from . import mail_tracking_event
from . import res_partner
from . import mail_thread
from . import mail_resend_message
+from . import mail_alias
diff --git a/mail_tracking/models/mail_alias.py b/mail_tracking/models/mail_alias.py
new file mode 100644
index 0000000..800259c
--- /dev/null
+++ b/mail_tracking/models/mail_alias.py
@@ -0,0 +1,33 @@
+# Copyright 2020 Alexandre Díaz
+# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).
+
+from odoo import api, models, tools
+
+
+class MailAlias(models.Model):
+ _inherit = "mail.alias"
+
+ @api.model
+ @tools.ormcache()
+ def get_aliases(self):
+ return {
+ x["display_name"]
+ for x in self.search_read([("alias_name", "!=", False)], ["display_name"])
+ }
+
+ @api.model_create_multi
+ def create(self, vals_list):
+ res = super().create(vals_list)
+ self.clear_caches()
+ return res
+
+ def write(self, vals):
+ res = super().write(vals)
+ if "alias_name" in vals:
+ self.clear_caches()
+ return res
+
+ def unlink(self):
+ res = super().unlink()
+ self.clear_caches()
+ return res
diff --git a/mail_tracking/models/mail_message.py b/mail_tracking/models/mail_message.py
index c0c818a..bc093bb 100644
--- a/mail_tracking/models/mail_message.py
+++ b/mail_tracking/models/mail_message.py
@@ -2,6 +2,8 @@
# Copyright 2019 Alexandre Díaz
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).
+from email.utils import getaddresses
+
from odoo import _, api, fields, models
from odoo.tools import email_split
@@ -13,6 +15,7 @@ class MailMessage(models.Model):
email_cc = fields.Char(
"Cc", help="Additional recipients that receive a " '"Carbon Copy" of the e-mail'
)
+ email_to = fields.Char("To", help="Raw TO recipients")
mail_tracking_ids = fields.One2many(
comodel_name="mail.tracking.email",
inverse_name="mail_message_id",
@@ -105,11 +108,16 @@ class MailMessage(models.Model):
.sudo()
.search([("mail_message_id", "=", message.id)])
)
- # Get Cc recipients
- email_cc_list = email_split(message.email_cc)
- if any(email_cc_list):
- partners |= partners.search([("email", "in", email_cc_list)])
+ # String to List
+ email_cc_list = self._drop_aliases(email_split(message.email_cc))
+ email_to_list = self._drop_aliases(email_split(message.email_to))
+ # Search related partners recipients
+ partners |= partners.search(
+ [("email", "in", email_cc_list + email_to_list)]
+ )
+ # Operate over set's instead of lists
email_cc_list = set(email_cc_list)
+ email_to_list = set(email_to_list) - email_cc_list
# Search all trackings for this message
for tracking in trackings:
status = self._partner_tracking_status_get(tracking)
@@ -127,45 +135,66 @@ class MailMessage(models.Model):
}
)
if tracking.partner_id:
+ # Discard mails with tracking
email_cc_list.discard(tracking.partner_id.email)
+ email_to_list.discard(tracking.partner_id.email)
partners_already |= tracking.partner_id
- # Search all recipients for this message
+ # Search all partner recipients for this message
if message.partner_ids:
partners |= message.partner_ids
if message.notified_partner_ids:
partners |= message.notified_partner_ids
- # Remove recipients already included
+ # Discard partner recipients already included
partners -= partners_already
- tracking_unkown_values = {
+ # Default tracking values
+ tracking_unknown_values = {
"status": "unknown",
"status_human": self._partner_tracking_status_human_get("unknown"),
"error_type": False,
"error_description": False,
"tracking_id": False,
}
+ # Process tracking status of partner recipients without tracking
for partner in partners:
+ # Discard 'To' with partner
+ if partner.email in email_to_list:
+ email_to_list.discard(partner.email)
# If there is partners not included, then status is 'unknown'
# and perhaps a Cc recipient
isCc = False
if partner.email in email_cc_list:
email_cc_list.discard(partner.email)
isCc = True
- tracking_unkown_values.update(
+ tracking_status = tracking_unknown_values.copy()
+ tracking_status.update(
{"recipient": partner.name, "partner_id": partner.id, "isCc": isCc}
)
- partner_trackings.append(tracking_unkown_values.copy())
- for email in email_cc_list:
- # If there is Cc without partner
- tracking_unkown_values.update(
- {"recipient": email, "partner_id": False, "isCc": True}
- )
- partner_trackings.append(tracking_unkown_values.copy())
+ partner_trackings.append(tracking_status)
+ # Process Cc/To recipients without partner
+ for cc, lst in [(True, email_cc_list), (False, email_to_list)]:
+ for email in lst:
+ tracking_status = tracking_unknown_values.copy()
+ tracking_status.update(
+ {"recipient": email, "partner_id": False, "isCc": cc}
+ )
+ partner_trackings.append(tracking_status)
res[message.id] = {
"partner_trackings": partner_trackings,
"is_failed_message": message.is_failed_message,
}
return res
+ @api.model
+ def _drop_aliases(self, mail_list):
+ aliases = self.env["mail.alias"].get_aliases()
+
+ def _filter_alias(email):
+ email_wn = getaddresses([email])[0][1]
+ if email_wn not in aliases:
+ return email_wn
+
+ return list(filter(_filter_alias, mail_list))
+
@api.model
def _message_read_dict_postprocess(self, messages, message_tree):
"""Preare values to be used by the chatter widget"""
diff --git a/mail_tracking/models/mail_thread.py b/mail_tracking/models/mail_thread.py
index 3b1102b..c2718cc 100644
--- a/mail_tracking/models/mail_thread.py
+++ b/mail_tracking/models/mail_thread.py
@@ -33,41 +33,48 @@ class MailThread(models.AbstractModel):
def message_post(self, *args, **kwargs):
"""Adds CC recipient to the message.
- Because Odoo implementation avoid store cc recipients we ensure that
- this information its written into the mail.message record.
+ Because Odoo implementation avoid store 'from, to, cc' recipients we
+ ensure that this information its written into the mail.message record.
"""
- new_message = super().message_post(*args, **kwargs)
- email_cc = kwargs.get("cc")
- if email_cc:
- new_message.sudo().write({"email_cc": email_cc})
- return new_message
+ kwargs.update(
+ {"email_cc": kwargs.get("cc", False), "email_to": kwargs.get("to", False)}
+ )
+ return super().message_post(*args, **kwargs)
def _message_get_suggested_recipients(self):
- """Adds email Cc recipients as suggested recipients.
+ """Adds email 'extra' recipients as suggested recipients.
If the recipient has a res.partner, use it.
"""
res = super()._message_get_suggested_recipients()
+ self._add_extra_recipients_suggestions(res, "email_cc", _("Cc"))
+ self._add_extra_recipients_suggestions(res, "email_to", _("Anon. To"))
+ return res
+
+ def _add_extra_recipients_suggestions(self, suggestions, field_mail, reason):
ResPartnerObj = self.env["res.partner"]
- email_cc_formated_list = []
+ aliases = self.env["mail.alias"].get_aliases()
+ email_extra_formated_list = []
for record in self:
- emails_cc = record.message_ids.mapped("email_cc")
- for email in emails_cc:
- email_cc_formated_list.extend(email_split_and_format(email))
- email_cc_formated_list = set(email_cc_formated_list)
- for cc in email_cc_formated_list:
- email_parts = getaddresses([cc])[0]
- partner_id = record._message_partner_info_from_emails([email_parts[1]])[
- 0
- ].get("partner_id")
+ emails_extra = record.message_ids.mapped(field_mail)
+ for email in emails_extra:
+ email_extra_formated_list.extend(email_split_and_format(email))
+ email_extra_formated_list = set(email_extra_formated_list)
+ email_extra_list = [x[1] for x in getaddresses(email_extra_formated_list)]
+ partners_info = self._message_partner_info_from_emails(email_extra_list)
+ for pinfo in partners_info:
+ partner_id = pinfo["partner_id"]
+ email = pinfo["full_name"]
if not partner_id:
- record._message_add_suggested_recipient(res, email=cc, reason=_("Cc"))
+ if email not in aliases:
+ self._message_add_suggested_recipient(
+ suggestions, email=email, reason=reason
+ )
else:
partner = ResPartnerObj.browse(partner_id)
- record._message_add_suggested_recipient(
- res, partner=partner, reason=_("Cc")
+ self._message_add_suggested_recipient(
+ suggestions, partner=partner, reason=reason
)
- return res
@api.model
def _fields_view_get(
diff --git a/mail_tracking/readme/USAGE.rst b/mail_tracking/readme/USAGE.rst
index aa63333..2488328 100644
--- a/mail_tracking/readme/USAGE.rst
+++ b/mail_tracking/readme/USAGE.rst
@@ -28,6 +28,9 @@ These are all available status icons:
.. |noemail| image:: ../static/src/img/no_email.png
:width: 10px
+.. |anonuser| image:: ../static/src/img/anon_user.png
+ :width: 10px
+
|unknown| **Unknown**: No email tracking info available. Maybe this notified partner has 'Receive Inbox Notifications by Email' == 'Never'
|waiting| **Waiting**: Waiting to be sent
@@ -44,6 +47,8 @@ These are all available status icons:
|noemail| **No Email**: The partner doesn't have a defined email
+|anonuser| **No Partner**: The recipient doesn't have a defined partner
+
If you want to see all tracking emails and events you can go to
diff --git a/mail_tracking/static/description/index.html b/mail_tracking/static/description/index.html
index 656a86f..61f9ec0 100644
--- a/mail_tracking/static/description/index.html
+++ b/mail_tracking/static/description/index.html
@@ -412,6 +412,7 @@ status icon will appear just right to name of notified partner.
Opened: Opened by partner
Cc: It’s a Carbon-Copy recipient. Can’t know the status so is ‘Unknown’
No Email: The partner doesn’t have a defined email
+ No Partner: The recipient doesn’t have a defined partner
If you want to see all tracking emails and events you can go to
- Settings > Technical > Email > Tracking emails
diff --git a/mail_tracking/static/src/img/anon_user.png b/mail_tracking/static/src/img/anon_user.png
new file mode 100644
index 0000000000000000000000000000000000000000..e57a7e2e080dcda2fefd0621e5697b39c1a3a792
GIT binary patch
literal 483
zcmV<90UZ8`P)S{Qv(y1L=T?3_V!1eK|WdFK_DQUj($Vpz(QRWZ0f8
zoW0OE)rjFMgMgTfjEp!B8-_MURKI<>w`b0TIeYJaMF??A8##x>N4hBSV0YxNd)w>t
zOQxNbNl7u{W?+zZ&ack*Qx{<15&U(cE5Cl@yoyxst_MZ1B+PIYzx!=DxjR5LD3N%9GAKK_|BZU6tjyR>b?nHN9NMA1?Sv4G4R
Z002<$9eSy1UU&ci002ovPDHLkV1j1v;mH61
literal 0
HcmV?d00001
diff --git a/mail_tracking/static/src/xml/mail_tracking.xml b/mail_tracking/static/src/xml/mail_tracking.xml
index 5144d16..37e4d2e 100644
--- a/mail_tracking/static/src/xml/mail_tracking.xml
+++ b/mail_tracking/static/src/xml/mail_tracking.xml
@@ -10,6 +10,11 @@
+
+
+
+
+
diff --git a/mail_tracking/tests/test_mail_tracking.py b/mail_tracking/tests/test_mail_tracking.py
index dd84926..ba9fefd 100644
--- a/mail_tracking/tests/test_mail_tracking.py
+++ b/mail_tracking/tests/test_mail_tracking.py
@@ -9,7 +9,7 @@ import psycopg2
import psycopg2.errorcodes
from lxml import etree
-from odoo import _, http
+from odoo import http
from odoo.tests.common import TransactionCase
from odoo.tools import mute_logger
@@ -179,8 +179,9 @@ class TestMailTracking(TransactionCase):
"login": "sender-test",
}
)
+ # pylint: disable=C8107
message = self.recipient.with_user(sender_user).message_post(
- body=_("This is a test message
"),
+ body="This is a test message
",
cc="unnamed@test.com, sender@example.com",
)
# suggested recipients