[FIX] mass_mailing_list_dynamic: Avoid error on shared contacts

- Create a contact with tag "X"
- Create a dynamic mailing list fully sync with criteria for tag "X".
- Sync it.
- Create a second mailing list non dynamic.
- Try to add the contact to second mailing list.

You get an error in this case, and it shouldn't happen.
pull/585/head
Pedro M. Baeza 2020-07-29 21:12:49 +02:00
parent e75f6f7aa9
commit 11067ea9cf
2 changed files with 58 additions and 8 deletions

View File

@ -1,5 +1,6 @@
# Copyright 2017 Tecnativa - Jairo Llopis
# Copyright 2019 Tecnativa - Victor M.M. Torres
# Copyright 2020 Tecnativa - Pedro M. Baeza
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).
from odoo import _, api, models
@ -9,13 +10,48 @@ from odoo.exceptions import ValidationError
class MassMailingContact(models.Model):
_inherit = "mail.mass_mailing.contact"
@api.constrains("partner_id", "list_ids", "name", "email")
def _check_no_manual_edits_on_fully_synced_lists(self):
def _check_dynamic_full_sync_list(self, mailing_list):
if mailing_list.dynamic and mailing_list.sync_method == "full":
raise ValidationError(_(
"Cannot edit manually contacts in a fully "
"synchronized list. Change its sync method or execute "
"a manual sync instead."
))
def _check_no_modification_on_fully_synced_lists(self, vals):
"""Check that no modification is done on fully synced dynamic list.
We examine then each possible command applied in the m2m field.
"""
if self.env.context.get("syncing"):
return
if any(self.mapped('list_ids').filtered(
lambda x: x.dynamic and x.sync_method == "full")):
raise ValidationError(
_("Cannot edit manually contacts in a fully "
"synchronized list. Change its sync method or execute "
"a manual sync instead."))
for command in vals["list_ids"]:
if command[0] in (1, 2, 3, 4):
lst = self.env["mail.mass_mailing.list"].browse(command[1])
self._check_dynamic_full_sync_list(lst)
elif command[0] in (5, 6):
for lst in self.mapped("list_ids"):
self._check_dynamic_full_sync_list(lst)
if command[0] == 6:
for _id in command[2]:
lst = self.env["mail.mass_mailing.list"].browse(_id)
self._check_dynamic_full_sync_list(lst)
@api.constrains("partner_id", "name", "email")
def _check_no_manual_edits_on_fully_synced_lists(self):
"""We have to avoid also changes in linked partner, name or email."""
if self.env.context.get("syncing"):
return
for lst in self.mapped('list_ids'):
self._check_dynamic_full_sync_list(lst)
def write(self, vals):
if "list_ids" in vals:
self._check_no_modification_on_fully_synced_lists(vals)
return super().write(vals)
@api.model_create_multi
def create(self, vals_list):
for vals in vals_list:
if "list_ids" in vals:
self._check_no_modification_on_fully_synced_lists(vals)
return super().create(vals_list)

View File

@ -136,3 +136,17 @@ class DynamicListCase(common.SavepointCase):
self.assertFalse(self.list.is_synced)
self.list.action_sync()
self.assertTrue(self.list.is_synced)
def test_no_edition_fully_synced_dynamic_list(self):
self.list.sync_method = "full"
contact = self.env["mail.mass_mailing.contact"].create({
"partner_id": self.partners[0].id,
})
with self.assertRaises(ValidationError):
contact.list_ids = [(4, self.list.id)]
# This one shouldn't fail
list2 = self.env["mail.mass_mailing.list"].create({
"name": "test list 2",
"dynamic": False,
})
contact.list_ids = [(4, list2.id)]