[IMP] (test_)mail: move and rewrite message tests related to channel or discuss
Purpose of this commit is to move moderation tests directly into mail channel test file. That way it is easier to maintain or update them as they are linked to that specific model and not global to mail.thread. Also containing * remove unnecessary tests or merge tests belonging to the same category; * make tests more readable; Followup of odoo/odoo@e9571a4 Followup of odoo/odoo@1fadb3ec5d Task ID-2421795 closes odoo/odoo#64501 Signed-off-by: Thibault Delavallee (tde) <tde@openerp.com>
This commit is contained in:
@@ -387,6 +387,101 @@ class TestChannelModeration(MailCommon):
|
||||
self.assertEqual(channel.channel_last_seen_partner_ids.partner_id, self.partner_employee | self.partner_root)
|
||||
self.assertEqual(channel.moderator_ids, self.user_employee)
|
||||
|
||||
@mute_logger('odoo.models.unlink')
|
||||
def test_message_moderate_ok(self):
|
||||
msg_c1_admin1 = self._add_messages(self.channel, 'Body11', author=self.partner_admin, moderation_status='pending_moderation')
|
||||
msg_c1_admin2 = self._add_messages(self.channel, 'Body12', author=self.partner_admin, moderation_status='pending_moderation')
|
||||
msg_c1_emplo2 = self._add_messages(self.channel, 'Body21', author=self.partner_employee_2, moderation_status='pending_moderation')
|
||||
|
||||
self._reset_bus()
|
||||
self.assertFalse(msg_c1_admin1.channel_ids | msg_c1_admin2.channel_ids | msg_c1_emplo2.channel_ids)
|
||||
|
||||
# accept
|
||||
msg_c1_admin1.with_user(self.user_employee)._moderate('accept')
|
||||
self.assertEqual(msg_c1_admin1.channel_ids, self.channel)
|
||||
self.assertEqual(msg_c1_admin1.moderation_status, 'accepted')
|
||||
self.assertEqual(msg_c1_admin2.moderation_status, 'pending_moderation')
|
||||
self.assertBusNotifications([(self.cr.dbname, 'mail.channel', self.channel.id)])
|
||||
|
||||
# allow
|
||||
self._reset_bus()
|
||||
(msg_c1_admin1 | msg_c1_emplo2).with_user(self.user_employee)._moderate('allow')
|
||||
self.assertEqual(msg_c1_admin1.channel_ids, self.channel)
|
||||
self.assertEqual(msg_c1_admin2.channel_ids, self.channel)
|
||||
self.assertEqual(msg_c1_emplo2.channel_ids, self.channel)
|
||||
self.assertEqual(msg_c1_admin1.moderation_status, 'accepted')
|
||||
self.assertEqual(msg_c1_admin2.moderation_status, 'accepted')
|
||||
self.assertEqual(msg_c1_emplo2.moderation_status, 'accepted')
|
||||
self.assertBusNotifications([
|
||||
(self.cr.dbname, 'mail.channel', self.channel.id),
|
||||
(self.cr.dbname, 'mail.channel', self.channel.id)])
|
||||
|
||||
@mute_logger('odoo.models.unlink')
|
||||
def test_message_moderate_reject(self):
|
||||
msg_c1_admin1 = self._add_messages(self.channel, '<p>Body11</p>', author=self.partner_admin, moderation_status='pending_moderation')
|
||||
msg_c1_admin2 = self._add_messages(self.channel, '<p>Body12</p>', author=self.partner_admin, moderation_status='pending_moderation')
|
||||
msg_c1_emplo2 = self._add_messages(self.channel, '<p>Body21</p>', author=self.partner_employee_2, moderation_status='pending_moderation')
|
||||
msg_c1_portal = self._add_messages(self.channel, '<p>Body12</p>', author=self.partner_portal, moderation_status='pending_moderation')
|
||||
id2, id4 = msg_c1_admin2.id, msg_c1_portal.id # save ids because unlink will discard them
|
||||
|
||||
self.assertFalse(msg_c1_admin1.channel_ids | msg_c1_admin2.channel_ids | msg_c1_emplo2.channel_ids | msg_c1_portal.channel_ids)
|
||||
|
||||
# test reject: should also send a rejection email
|
||||
with self.mock_mail_gateway():
|
||||
(msg_c1_admin1 | msg_c1_emplo2).with_user(self.user_employee)._moderate('reject', title='RejectTitle', comment='RejectComment')
|
||||
self.assertEqual(len(self._new_mails), 2)
|
||||
|
||||
self.assertMailMailWEmails([self.partner_admin.email_formatted, self.partner_employee_2.email_formatted], 'outgoing', 'RejectComment',
|
||||
fields_values={'subject': 'RejectTitle', 'author_id': self.partner_employee})
|
||||
self.assertTrue(all('RejectComment' in body for body in self._new_mails.mapped('body_html')))
|
||||
self.assertTrue(all('Body' in body for body in self._new_mails.mapped('body_html')))
|
||||
|
||||
# test discard: silently remove
|
||||
self._reset_bus()
|
||||
(msg_c1_admin2 + msg_c1_portal).with_user(self.user_employee)._moderate_discard()
|
||||
|
||||
# check all generated bus notifications
|
||||
self.assertBusNotifications(
|
||||
[(self.cr.dbname, 'res.partner', self.partner_admin.id),
|
||||
(self.cr.dbname, 'res.partner', self.partner_employee.id),
|
||||
(self.cr.dbname, 'res.partner', self.partner_portal.id)],
|
||||
[{'type': 'deletion', 'message_ids': [id2]}, # author of 1 message
|
||||
{'type': 'deletion', 'message_ids': [id2, id4]}, # moderator
|
||||
{'type': 'deletion', 'message_ids': [id4]}] # author of 1 message
|
||||
)
|
||||
|
||||
@mute_logger('odoo.models.unlink')
|
||||
def test_message_notify_moderators(self):
|
||||
# create pending messages in another channel to have two notification to push
|
||||
msg_c1_admin1 = self._add_messages(self.channel, '<p>Body11</p>', author=self.partner_admin, moderation_status='pending_moderation')
|
||||
msg_c1_admin2 = self._add_messages(self.channel, '<p>Body12</p>', author=self.partner_admin, moderation_status='pending_moderation')
|
||||
msg_c1_portal = self._add_messages(self.channel, '<p>Body21</p>', author=self.partner_employee_2, moderation_status='pending_moderation')
|
||||
|
||||
channel_2 = self.env['mail.channel'].create({
|
||||
'name': 'Moderation_1',
|
||||
'email_send': True,
|
||||
'moderation': True,
|
||||
'channel_partner_ids': [(4, self.partner_admin.id)],
|
||||
'moderator_ids': [(4, self.user_admin.id)],
|
||||
})
|
||||
msg_c2_portal = self._add_messages(channel_2, 'Body31', author=self.partner_employee_2, moderation_status='pending_moderation')
|
||||
|
||||
# one notification for each moderator: employee (channel1), admin (channel2)
|
||||
with self.assertPostNotifications([{
|
||||
'content': 'Hello %s' % self.partner_employee.name,
|
||||
'message_type': 'user_notification', 'subtype': 'mail.mt_note',
|
||||
'notif': [{
|
||||
'partner': self.partner_employee,
|
||||
'type': 'inbox'}]
|
||||
}, {
|
||||
'content': 'Hello %s' % self.partner_admin.name,
|
||||
'message_type': 'user_notification', 'subtype': 'mail.mt_note',
|
||||
'notif': [{
|
||||
'partner': self.partner_admin,
|
||||
'type': 'inbox'}]
|
||||
}]):
|
||||
self.env['mail.message']._notify_moderators()
|
||||
|
||||
@users('employee')
|
||||
def test_moderation_fields(self):
|
||||
channel = self.env['mail.channel'].browse(self.channel.ids)
|
||||
|
||||
@@ -378,180 +378,3 @@ class TestMessageAccess(TestMailCommon):
|
||||
self.message.write({'model': 'mail.channel', 'res_id': self.group_public.id, 'moderation_status': 'pending_moderation'})
|
||||
with self.assertRaises(AccessError):
|
||||
self.message.with_user(self.user_employee).write({'moderation_status': 'accepted'})
|
||||
|
||||
@mute_logger('openerp.addons.mail.models.mail_mail')
|
||||
def test_mark_all_as_read(self):
|
||||
self.user_employee.notification_type = 'inbox'
|
||||
emp_partner = self.user_employee.partner_id.with_user(self.user_employee)
|
||||
|
||||
group_private = self.env['mail.channel'].with_context({
|
||||
'mail_create_nolog': True,
|
||||
'mail_create_nosubscribe': True,
|
||||
'mail_channel_noautofollow': True,
|
||||
}).create({
|
||||
'name': 'Private',
|
||||
'description': 'Private James R.',
|
||||
'public': 'private',
|
||||
'alias_name': 'private',
|
||||
'alias_contact': 'followers'}
|
||||
).with_context({'mail_create_nosubscribe': False})
|
||||
|
||||
# mark all as read clear needactions
|
||||
msg1 = group_private.message_post(body='Test', message_type='comment', subtype_xmlid='mail.mt_comment', partner_ids=[emp_partner.id])
|
||||
self._reset_bus()
|
||||
emp_partner.env['mail.message'].mark_all_as_read(domain=[])
|
||||
self.assertBusNotifications([(self.cr.dbname, 'res.partner', emp_partner.id)], [{ 'type': 'mark_as_read', 'message_ids': [msg1.id] }])
|
||||
na_count = emp_partner.get_needaction_count()
|
||||
self.assertEqual(na_count, 0, "mark all as read should conclude all needactions")
|
||||
|
||||
# mark all as read also clear inaccessible needactions
|
||||
msg2 = group_private.message_post(body='Zest', message_type='comment', subtype_xmlid='mail.mt_comment', partner_ids=[emp_partner.id])
|
||||
needaction_accessible = len(emp_partner.env['mail.message'].search([['needaction', '=', True]]))
|
||||
self.assertEqual(needaction_accessible, 1, "a new message to a partner is readable to that partner")
|
||||
|
||||
msg2.sudo().partner_ids = self.env['res.partner']
|
||||
emp_partner.env['mail.message'].search([['needaction', '=', True]])
|
||||
needaction_length = len(emp_partner.env['mail.message'].search([['needaction', '=', True]]))
|
||||
self.assertEqual(needaction_length, 1, "message should still be readable when notified")
|
||||
|
||||
na_count = emp_partner.get_needaction_count()
|
||||
self.assertEqual(na_count, 1, "message not accessible is currently still counted")
|
||||
|
||||
self._reset_bus()
|
||||
emp_partner.env['mail.message'].mark_all_as_read(domain=[])
|
||||
self.assertBusNotifications([(self.cr.dbname, 'res.partner', emp_partner.id)], [{ 'type': 'mark_as_read', 'message_ids': [msg2.id] }])
|
||||
na_count = emp_partner.get_needaction_count()
|
||||
self.assertEqual(na_count, 0, "mark all read should conclude all needactions even inacessible ones")
|
||||
|
||||
@mute_logger('openerp.addons.mail.models.mail_mail')
|
||||
def test_mark_all_as_read_share(self):
|
||||
self.user_portal.notification_type = 'inbox'
|
||||
portal_partner = self.user_portal.partner_id.with_user(self.user_portal)
|
||||
|
||||
# mark all as read clear needactions
|
||||
self.group_pigs.message_post(body='Test', message_type='comment', subtype_xmlid='mail.mt_comment', partner_ids=[portal_partner.id])
|
||||
portal_partner.env['mail.message'].mark_all_as_read(domain=[])
|
||||
na_count = portal_partner.get_needaction_count()
|
||||
self.assertEqual(na_count, 0, "mark all as read should conclude all needactions")
|
||||
|
||||
# mark all as read also clear inaccessible needactions
|
||||
new_msg = self.group_pigs.message_post(body='Zest', message_type='comment', subtype_xmlid='mail.mt_comment', partner_ids=[portal_partner.id])
|
||||
needaction_accessible = len(portal_partner.env['mail.message'].search([['needaction', '=', True]]))
|
||||
self.assertEqual(needaction_accessible, 1, "a new message to a partner is readable to that partner")
|
||||
|
||||
new_msg.sudo().partner_ids = self.env['res.partner']
|
||||
needaction_length = len(portal_partner.env['mail.message'].search([['needaction', '=', True]]))
|
||||
self.assertEqual(needaction_length, 1, "message should still be readable when notified")
|
||||
|
||||
na_count = portal_partner.get_needaction_count()
|
||||
self.assertEqual(na_count, 1, "message not accessible is currently still counted")
|
||||
|
||||
portal_partner.env['mail.message'].mark_all_as_read(domain=[])
|
||||
na_count = portal_partner.get_needaction_count()
|
||||
self.assertEqual(na_count, 0, "mark all read should conclude all needactions even inacessible ones")
|
||||
|
||||
|
||||
@tagged('moderation')
|
||||
class TestMessageModeration(TestMailCommon):
|
||||
|
||||
@classmethod
|
||||
def setUpClass(cls):
|
||||
super(TestMessageModeration, cls).setUpClass()
|
||||
|
||||
cls.channel_1 = cls.env['mail.channel'].create({
|
||||
'name': 'Moderation_1',
|
||||
'email_send': True,
|
||||
'moderation': True
|
||||
})
|
||||
cls.user_employee.write({'moderation_channel_ids': [(6, 0, [cls.channel_1.id])]})
|
||||
cls.user_portal = cls._create_portal_user()
|
||||
|
||||
# A pending moderation message needs to have field channel_ids empty. Moderators
|
||||
# need to be able to notify a pending moderation message (in a channel they moderate).
|
||||
cls.msg_c1_admin1 = cls._add_messages(cls.channel_1, 'Body11', author=cls.partner_admin, moderation_status='pending_moderation')
|
||||
cls.msg_c1_admin2 = cls._add_messages(cls.channel_1, 'Body12', author=cls.partner_admin, moderation_status='pending_moderation')
|
||||
cls.msg_c1_portal = cls._add_messages(cls.channel_1, 'Body21', author=cls.partner_portal, moderation_status='pending_moderation')
|
||||
|
||||
@mute_logger('odoo.models.unlink')
|
||||
def test_moderate_accept(self):
|
||||
self._reset_bus()
|
||||
self.assertFalse(self.msg_c1_admin1.channel_ids | self.msg_c1_admin2.channel_ids | self.msg_c1_portal.channel_ids)
|
||||
|
||||
self.msg_c1_admin1.with_user(self.user_employee)._moderate('accept')
|
||||
self.assertEqual(self.msg_c1_admin1.channel_ids, self.channel_1)
|
||||
self.assertEqual(self.msg_c1_admin1.moderation_status, 'accepted')
|
||||
self.assertEqual(self.msg_c1_admin2.moderation_status, 'pending_moderation')
|
||||
self.assertBusNotifications([(self.cr.dbname, 'mail.channel', self.channel_1.id)])
|
||||
|
||||
@mute_logger('odoo.models.unlink')
|
||||
def test_moderate_allow(self):
|
||||
self._reset_bus()
|
||||
|
||||
self.msg_c1_admin1.with_user(self.user_employee)._moderate('allow')
|
||||
self.assertEqual(self.msg_c1_admin1.channel_ids, self.channel_1)
|
||||
self.assertEqual(self.msg_c1_admin2.channel_ids, self.channel_1)
|
||||
self.assertEqual(self.msg_c1_admin1.moderation_status, 'accepted')
|
||||
self.assertEqual(self.msg_c1_admin2.moderation_status, 'accepted')
|
||||
self.assertBusNotifications([
|
||||
(self.cr.dbname, 'mail.channel', self.channel_1.id),
|
||||
(self.cr.dbname, 'mail.channel', self.channel_1.id)])
|
||||
|
||||
@mute_logger('odoo.models.unlink')
|
||||
def test_moderate_reject(self):
|
||||
with self.mock_mail_gateway():
|
||||
(self.msg_c1_admin1 | self.msg_c1_portal).with_user(self.user_employee)._moderate_send_reject_email('Title', 'Message to author')
|
||||
self.assertEqual(len(self._new_mails), 2)
|
||||
for mail in self._new_mails:
|
||||
self.assertEqual(mail.author_id, self.partner_employee)
|
||||
self.assertEqual(mail.subject, 'Title')
|
||||
self.assertEqual(mail.state, 'outgoing')
|
||||
self.assertEqual(
|
||||
set(self._new_mails.mapped('email_to')),
|
||||
set([self.msg_c1_admin1.email_from, self.msg_c1_portal.email_from])
|
||||
)
|
||||
self.assertEqual(
|
||||
set(self._new_mails.mapped('body_html')),
|
||||
set(['<div>Message to author</div>\n%s\n' % self.msg_c1_admin1.body, '<div>Message to author</div>\n%s\n' % self.msg_c1_portal.body])
|
||||
) # TDE note: \n are added by append content to html, because why not
|
||||
|
||||
@mute_logger('odoo.models.unlink')
|
||||
def test_moderate_discard(self):
|
||||
self._reset_bus()
|
||||
id1, id2, id3 = self.msg_c1_admin1.id, self.msg_c1_admin2.id, self.msg_c1_portal.id # save ids because unlink will discard them
|
||||
(self.msg_c1_admin1 | self.msg_c1_admin2 | self.msg_c1_portal).with_user(self.user_employee)._moderate_discard()
|
||||
|
||||
self.assertBusNotifications(
|
||||
[(self.cr.dbname, 'res.partner', self.partner_admin.id),
|
||||
(self.cr.dbname, 'res.partner', self.partner_employee.id),
|
||||
(self.cr.dbname, 'res.partner', self.partner_portal.id)],
|
||||
[{'type': 'deletion', 'message_ids': [id1, id2]}, # author of 2 messages
|
||||
{'type': 'deletion', 'message_ids': [id1, id2, id3]}, # moderator
|
||||
{'type': 'deletion', 'message_ids': [id3]}] # author of 1 message
|
||||
)
|
||||
|
||||
@mute_logger('odoo.models.unlink')
|
||||
def test_notify_moderators(self):
|
||||
# create pending messages in another channel to have two notification to push
|
||||
channel_2 = self.env['mail.channel'].create({
|
||||
'name': 'Moderation_1',
|
||||
'email_send': True,
|
||||
'moderation': True
|
||||
})
|
||||
self.user_admin.write({'moderation_channel_ids': [(6, 0, [channel_2.id])]})
|
||||
self.msg_c2_portal = self._add_messages(channel_2, 'Body31', author=self.partner_portal, moderation_status='pending_moderation')
|
||||
|
||||
# one notification for each moderator: employee (channel1), admin (channel2)
|
||||
with self.assertPostNotifications([{
|
||||
'content': 'Hello %s' % self.partner_employee.name,
|
||||
'message_type': 'user_notification', 'subtype': 'mail.mt_note',
|
||||
'notif': [{
|
||||
'partner': self.partner_employee,
|
||||
'type': 'inbox'}]
|
||||
}, {
|
||||
'content': 'Hello %s' % self.partner_admin.name,
|
||||
'message_type': 'user_notification', 'subtype': 'mail.mt_note',
|
||||
'notif': [{
|
||||
'partner': self.partner_admin,
|
||||
'type': 'inbox'}]
|
||||
}]):
|
||||
self.env['mail.message']._notify_moderators()
|
||||
|
||||
@@ -1,8 +1,12 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
from unittest.mock import patch
|
||||
from unittest.mock import DEFAULT
|
||||
from werkzeug.urls import url_parse, url_decode
|
||||
|
||||
from odoo import exceptions
|
||||
from odoo.addons.test_mail.models.test_mail_models import MailTestSimple
|
||||
from odoo.addons.test_mail.tests.common import TestMailCommon, TestRecipients
|
||||
from odoo.tests.common import tagged, HttpCase
|
||||
from odoo.tools import mute_logger
|
||||
@@ -107,7 +111,54 @@ class TestDiscuss(TestMailCommon, TestRecipients):
|
||||
@classmethod
|
||||
def setUpClass(cls):
|
||||
super(TestDiscuss, cls).setUpClass()
|
||||
cls.test_record = cls.env['mail.test.simple'].with_context(cls._test_context).create({'name': 'Test', 'email_from': 'ignasse@example.com'})
|
||||
cls.test_record = cls.env['mail.test.simple'].with_context(cls._test_context).create({
|
||||
'name': 'Test',
|
||||
'email_from': 'ignasse@example.com'
|
||||
})
|
||||
|
||||
@mute_logger('openerp.addons.mail.models.mail_mail')
|
||||
def test_mark_all_as_read(self):
|
||||
def _employee_crash(*args, **kwargs):
|
||||
""" If employee is test employee, consider he has no access on document """
|
||||
recordset = args[0]
|
||||
if recordset.env.uid == self.user_employee.id and not recordset.env.su:
|
||||
if kwargs.get('raise_exception', True):
|
||||
raise exceptions.AccessError('Hop hop hop Ernest, please step back.')
|
||||
return False
|
||||
return DEFAULT
|
||||
|
||||
with patch.object(MailTestSimple, 'check_access_rights', autospec=True, side_effect=_employee_crash):
|
||||
with self.assertRaises(exceptions.AccessError):
|
||||
self.env['mail.test.simple'].with_user(self.user_employee).browse(self.test_record.ids).read(['name'])
|
||||
|
||||
employee_partner = self.env['res.partner'].with_user(self.user_employee).browse(self.partner_employee.ids)
|
||||
|
||||
# mark all as read clear needactions
|
||||
msg1 = self.test_record.message_post(body='Test', message_type='comment', subtype_xmlid='mail.mt_comment', partner_ids=[employee_partner.id])
|
||||
self._reset_bus()
|
||||
employee_partner.env['mail.message'].mark_all_as_read(domain=[])
|
||||
self.assertBusNotifications([(self.cr.dbname, 'res.partner', employee_partner.id)], [{ 'type': 'mark_as_read', 'message_ids': [msg1.id] }])
|
||||
na_count = employee_partner.get_needaction_count()
|
||||
self.assertEqual(na_count, 0, "mark all as read should conclude all needactions")
|
||||
|
||||
# mark all as read also clear inaccessible needactions
|
||||
msg2 = self.test_record.message_post(body='Zest', message_type='comment', subtype_xmlid='mail.mt_comment', partner_ids=[employee_partner.id])
|
||||
needaction_accessible = len(employee_partner.env['mail.message'].search([['needaction', '=', True]]))
|
||||
self.assertEqual(needaction_accessible, 1, "a new message to a partner is readable to that partner")
|
||||
|
||||
msg2.sudo().partner_ids = self.env['res.partner']
|
||||
employee_partner.env['mail.message'].search([['needaction', '=', True]])
|
||||
needaction_length = len(employee_partner.env['mail.message'].search([['needaction', '=', True]]))
|
||||
self.assertEqual(needaction_length, 1, "message should still be readable when notified")
|
||||
|
||||
na_count = employee_partner.get_needaction_count()
|
||||
self.assertEqual(na_count, 1, "message not accessible is currently still counted")
|
||||
|
||||
self._reset_bus()
|
||||
employee_partner.env['mail.message'].mark_all_as_read(domain=[])
|
||||
self.assertBusNotifications([(self.cr.dbname, 'res.partner', employee_partner.id)], [{ 'type': 'mark_as_read', 'message_ids': [msg2.id] }])
|
||||
na_count = employee_partner.get_needaction_count()
|
||||
self.assertEqual(na_count, 0, "mark all read should conclude all needactions even inacessible ones")
|
||||
|
||||
def test_set_message_done_user(self):
|
||||
with self.assertSinglePostNotifications([{'partner': self.partner_employee, 'type': 'inbox'}], message_info={'content': 'Test'}):
|
||||
|
||||
Reference in New Issue
Block a user