[MERGE] Revisions 9000 ... 9002 of 7.0 branch
bzr revid: tde@openerp.com-20130426132847-mr8e0yuxao582bs6
This commit is contained in:
@@ -982,6 +982,16 @@ class crm_lead(base_stage, format_address, osv.osv):
|
||||
return [lead.section_id.message_get_reply_to()[0] if lead.section_id else False
|
||||
for lead in self.browse(cr, uid, ids, context=context)]
|
||||
|
||||
def _get_document_action(self, cr, uid, id, context=None):
|
||||
action = super(crm_lead, self)._get_document_action(cr, uid, id, context=context)
|
||||
obj = self.browse(cr, uid, id, context=context)
|
||||
if obj.type == 'opportunity':
|
||||
model, view_id = self.pool.get('ir.model.data').get_object_reference(cr, uid, 'crm', 'crm_case_form_view_oppor')
|
||||
action.update({
|
||||
'views': [(view_id, 'form')],
|
||||
})
|
||||
return action
|
||||
|
||||
def message_get_suggested_recipients(self, cr, uid, ids, context=None):
|
||||
recipients = super(crm_lead, self).message_get_suggested_recipients(cr, uid, ids, context=context)
|
||||
for lead in self.browse(cr, uid, ids, context=context):
|
||||
|
||||
@@ -198,6 +198,16 @@ class mail_mail(osv.Model):
|
||||
# mail_mail formatting, tools and send mechanism
|
||||
#------------------------------------------------------
|
||||
|
||||
# TDE NOTE: as for 7.0 link generation is located in mail.mail because it grew
|
||||
# based on a simple URL generation that moved towards something more complicated
|
||||
# Moreover a bug in hierarchy generation prevents from putting link generation
|
||||
# inside mail_thread and override it in modules; the overrides will not be
|
||||
# taken into account
|
||||
# TODO in 8.0: maybe factorize this to enable in modules link generation
|
||||
# independently of mail_mail model
|
||||
# TODO in 8.0: factorize doc name sanitized and 'Followers of ...' formatting
|
||||
# because it begins to appear everywhere
|
||||
|
||||
def _get_partner_access_link(self, cr, uid, mail, partner=None, context=None):
|
||||
""" Generate URLs for links in mails:
|
||||
- partner is an user and has read access to the document: direct link to document with model, res_id
|
||||
|
||||
+27
-14
@@ -33,7 +33,7 @@ from email.message import Message
|
||||
from openerp import tools
|
||||
from openerp import SUPERUSER_ID
|
||||
from openerp.addons.mail.mail_message import decode
|
||||
from openerp.osv import fields, osv
|
||||
from openerp.osv import fields, osv, orm
|
||||
from openerp.tools.safe_eval import safe_eval as eval
|
||||
from openerp.tools.translate import _
|
||||
|
||||
@@ -449,7 +449,24 @@ class mail_thread(osv.AbstractModel):
|
||||
ir_attachment_obj.unlink(cr, uid, attach_ids, context=context)
|
||||
return True
|
||||
|
||||
def message_redirect_get_inbox_action_xml_id(self, cr, uid, context=None):
|
||||
def _get_document_action(self, cr, uid, id, model=None, context=None):
|
||||
""" Return an action to open the document. This method is meant to be
|
||||
overridden in addons that want to give specific view ids for example.
|
||||
|
||||
:param int id: id of the document to open
|
||||
:param string model: specific model that overrides self._name
|
||||
"""
|
||||
return {
|
||||
'type': 'ir.actions.act_window',
|
||||
'res_model': model or self._name,
|
||||
'view_type': 'form',
|
||||
'view_mode': 'form',
|
||||
'views': [(False, 'form')],
|
||||
'target': 'current',
|
||||
'res_id': id,
|
||||
}
|
||||
|
||||
def _get_inbox_action_xml_id(self, cr, uid, context=None):
|
||||
""" When redirecting towards the Inbox, choose which action xml_id has
|
||||
to be fetched. This method is meant to be inherited, at least in portal
|
||||
because portal users have a different Inbox action than classic users. """
|
||||
@@ -469,7 +486,7 @@ class mail_thread(osv.AbstractModel):
|
||||
|
||||
# default action is the Inbox action
|
||||
self.pool.get('res.users').browse(cr, SUPERUSER_ID, uid, context=context)
|
||||
act_model, act_id = self.pool.get('ir.model.data').get_object_reference(cr, uid, *self.message_redirect_get_inbox_action_xml_id(cr, uid, context=context))
|
||||
act_model, act_id = self.pool.get('ir.model.data').get_object_reference(cr, uid, *self._get_inbox_action_xml_id(cr, uid, context=context))
|
||||
action = self.pool.get(act_model).read(cr, uid, act_id, [])
|
||||
|
||||
# if msg_id specified: try to redirect to the document or fallback on the Inbox
|
||||
@@ -479,17 +496,13 @@ class mail_thread(osv.AbstractModel):
|
||||
msg = self.pool.get('mail.message').browse(cr, uid, msg_id, context=context)
|
||||
if msg.model and msg.res_id and self.pool.get(msg.model).check_access_rights(cr, uid, 'read', raise_exception=False):
|
||||
try:
|
||||
self.pool.get(msg.model).check_access_rule(cr, uid, [msg.res_id], 'read', context=context)
|
||||
action = {
|
||||
'type': 'ir.actions.act_window',
|
||||
'res_model': msg.model,
|
||||
'view_type': 'form',
|
||||
'view_mode': 'form',
|
||||
'views': [(msg.res_id, 'form')],
|
||||
'target': 'current',
|
||||
'res_id': msg.res_id,
|
||||
}
|
||||
except osv.except_osv:
|
||||
model_obj = self.pool.get(msg.model)
|
||||
model_obj.check_access_rule(cr, uid, [msg.res_id], 'read', context=context)
|
||||
if not hasattr(model_obj, '_get_document_action'):
|
||||
action = self.pool.get('mail.thread')._get_document_action(cr, uid, msg.res_id, model=msg.model, context=context)
|
||||
else:
|
||||
action = model_obj._get_document_action(cr, uid, msg.res_id, context=context)
|
||||
except (osv.except_osv, orm.except_orm):
|
||||
action.update({
|
||||
'context': {
|
||||
'search_default_model': msg.model,
|
||||
|
||||
@@ -19,12 +19,15 @@
|
||||
#
|
||||
##############################################################################
|
||||
|
||||
from openerp.addons.mail.mail_mail import mail_mail
|
||||
from openerp.addons.mail.mail_thread import mail_thread
|
||||
from openerp.addons.mail.tests.test_mail_base import TestMailBase
|
||||
from openerp.tools import mute_logger
|
||||
from openerp.tools.mail import html_sanitize
|
||||
|
||||
|
||||
class test_mail(TestMailBase):
|
||||
|
||||
|
||||
def test_000_alias_setup(self):
|
||||
""" Test basic mail.alias setup works, before trying to use them for routing """
|
||||
cr, uid = self.cr, self.uid
|
||||
@@ -43,7 +46,6 @@ class test_mail(TestMailBase):
|
||||
self.user_barty = self.res_users.browse(cr, uid, self.user_barty_id)
|
||||
self.assertEquals(self.user_barty.alias_name, 'b4r+_-_r3wl-', 'Disallowed chars should be replaced by hyphens')
|
||||
|
||||
|
||||
def test_00_followers_function_field(self):
|
||||
""" Tests designed for the many2many function field 'follower_ids'.
|
||||
We will test to perform writes using the many2many commands 0, 3, 4,
|
||||
@@ -171,6 +173,64 @@ class test_mail(TestMailBase):
|
||||
self.assertNotIn('First answer, should not be displayed', result, 'Old answer should not be in quote.')
|
||||
self.assertNotIn('My answer I am propagating', result, 'Thread header content should be in quote.')
|
||||
|
||||
def test_11_notification_url(self):
|
||||
""" Tests designed to test the URL added in notification emails. """
|
||||
cr, uid, group_pigs = self.cr, self.uid, self.group_pigs
|
||||
|
||||
# Partner data
|
||||
partner_raoul = self.res_partner.browse(cr, uid, self.partner_raoul_id)
|
||||
partner_bert_id = self.res_partner.create(cr, uid, {'name': 'bert'})
|
||||
partner_bert = self.res_partner.browse(cr, uid, partner_bert_id)
|
||||
# Mail data
|
||||
mail_mail_id = self.mail_mail.create(cr, uid, {'state': 'exception'})
|
||||
mail = self.mail_mail.browse(cr, uid, mail_mail_id)
|
||||
|
||||
# Test: link for nobody -> None
|
||||
url = mail_mail._get_partner_access_link(self.mail_mail, cr, uid, mail)
|
||||
self.assertEqual(url, None,
|
||||
'notification email: mails not send to a specific partner should not have any URL')
|
||||
|
||||
# Test: link for partner -> None
|
||||
url = mail_mail._get_partner_access_link(self.mail_mail, cr, uid, mail, partner=partner_bert)
|
||||
self.assertEqual(url, None,
|
||||
'notification email: mails send to a not-user partner should not have any URL')
|
||||
|
||||
# Test: link for user -> signin
|
||||
url = mail_mail._get_partner_access_link(self.mail_mail, cr, uid, mail, partner=partner_raoul)
|
||||
self.assertIn('action=mail.action_mail_redirect', url,
|
||||
'notification email: link should contain the redirect action')
|
||||
self.assertIn('login=%s' % partner_raoul.user_ids[0].login, url,
|
||||
'notification email: link should contain the user login')
|
||||
|
||||
@mute_logger('openerp.addons.mail.mail_thread', 'openerp.osv.orm')
|
||||
def test_12_inbox_redirection(self):
|
||||
""" Tests designed to test the inbox redirection of emails notification URLs. """
|
||||
cr, uid, user_admin, group_pigs = self.cr, self.uid, self.user_admin, self.group_pigs
|
||||
model, act_id = self.ir_model_data.get_object_reference(cr, uid, 'mail', 'action_mail_inbox_feeds')
|
||||
# Data: post a message on pigs
|
||||
msg_id = self.group_pigs.message_post(body='My body', partner_ids=[self.partner_bert_id], type='comment', subtype='mail.mt_comment')
|
||||
|
||||
# No specific parameters -> should redirect to Inbox
|
||||
action = mail_thread.message_redirect_action(self.mail_thread, cr, self.user_raoul_id, {'params': {}})
|
||||
self.assertEqual(action.get('type'), 'ir.actions.client',
|
||||
'URL redirection: action without parameters should redirect to client action Inbox')
|
||||
self.assertEqual(action.get('id'), act_id,
|
||||
'URL redirection: action without parameters should redirect to client action Inbox')
|
||||
|
||||
# Bert has read access to Pigs -> should redirect to form view of Pigs
|
||||
action = mail_thread.message_redirect_action(self.mail_thread, cr, self.user_raoul_id, {'params': {'message_id': msg_id}})
|
||||
self.assertEqual(action.get('type'), 'ir.actions.act_window',
|
||||
'URL redirection: action with message_id for read-accredited user should redirect to Pigs')
|
||||
self.assertEqual(action.get('res_id'), group_pigs.id,
|
||||
'URL redirection: action with message_id for read-accredited user should redirect to Pigs')
|
||||
|
||||
# Bert has no read access to Pigs -> should redirect to Inbox
|
||||
action = mail_thread.message_redirect_action(self.mail_thread, cr, self.user_bert_id, {'params': {'message_id': msg_id}})
|
||||
self.assertEqual(action.get('type'), 'ir.actions.client',
|
||||
'URL redirection: action without parameters should redirect to client action Inbox')
|
||||
self.assertEqual(action.get('id'), act_id,
|
||||
'URL redirection: action without parameters should redirect to client action Inbox')
|
||||
|
||||
def test_20_message_post(self):
|
||||
""" Tests designed for message_post. """
|
||||
cr, uid, user_raoul, group_pigs = self.cr, self.uid, self.user_raoul, self.group_pigs
|
||||
|
||||
@@ -0,0 +1,44 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
##############################################################################
|
||||
#
|
||||
# OpenERP, Open Source Management Solution
|
||||
# Copyright (C) 2013-TODAY OpenERP S.A (<http://www.openerp.com>).
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as
|
||||
# published by the Free Software Foundation, either version 3 of the
|
||||
# License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
##############################################################################
|
||||
|
||||
from openerp import SUPERUSER_ID
|
||||
from openerp.osv import osv
|
||||
|
||||
|
||||
class mail_thread(osv.AbstractModel):
|
||||
""" Update of mail_mail class, to add the signin URL to notifications. """
|
||||
_inherit = 'mail.thread'
|
||||
|
||||
def _get_inbox_action_xml_id(self, cr, uid, context=None):
|
||||
""" For a given message, return an action that either
|
||||
- opens the form view of the related document if model, res_id, and
|
||||
read access to the document
|
||||
- opens the Inbox with a default search on the conversation if model,
|
||||
res_id
|
||||
- opens the Inbox with context propagated
|
||||
"""
|
||||
# if uid is a portal user -> action is different
|
||||
portal_model, group_id = self.pool.get('ir.model.data').get_object_reference(cr, uid, 'portal', 'group_portal')
|
||||
cur_user = self.pool.get('res.users').browse(cr, SUPERUSER_ID, uid, context=context)
|
||||
if group_id in [g.id for g in cur_user.groups_id]:
|
||||
return ('portal', 'action_mail_inbox_feeds_portal')
|
||||
else:
|
||||
return super(mail_thread, self)._get_inbox_action_xml_id(cr, uid, context=context)
|
||||
@@ -130,3 +130,70 @@ class test_portal(TestMailBase):
|
||||
'invite: body of invitation email is incorrect')
|
||||
self.assertTrue(partner_carine.signup_url in sent_email.get('body'),
|
||||
'invite: body of invitation email does not contain signup url')
|
||||
|
||||
def test_20_notification_url(self):
|
||||
""" Tests designed to test the URL added in notification emails. """
|
||||
cr, uid, group_pigs = self.cr, self.uid, self.group_pigs
|
||||
|
||||
# Partner data
|
||||
partner_raoul = self.res_partner.browse(cr, uid, self.partner_raoul_id)
|
||||
partner_bert_id = self.res_partner.create(cr, uid, {'name': 'bert'})
|
||||
partner_bert = self.res_partner.browse(cr, uid, partner_bert_id)
|
||||
# Mail data
|
||||
mail_mail_id = self.mail_mail.create(cr, uid, {'state': 'exception'})
|
||||
mail = self.mail_mail.browse(cr, uid, mail_mail_id)
|
||||
|
||||
# Test: link for nobody -> None
|
||||
url = self.mail_mail._get_partner_access_link(cr, uid, mail)
|
||||
self.assertEqual(url, None,
|
||||
'notification email: mails not send to a specific partner should not have any URL')
|
||||
|
||||
# Test: link for partner -> signup URL
|
||||
url = self.mail_mail._get_partner_access_link(cr, uid, mail, partner=partner_bert)
|
||||
self.assertIn(partner_bert.signup_url, url,
|
||||
'notification email: mails send to a not-user partner should contain the signup URL')
|
||||
|
||||
# Test: link for user -> signin
|
||||
url = self.mail_mail._get_partner_access_link(cr, uid, mail, partner=partner_raoul)
|
||||
self.assertIn('action=mail.action_mail_redirect', url,
|
||||
'notification email: link should contain the redirect action')
|
||||
self.assertIn('login=%s' % partner_raoul.user_ids[0].login, url,
|
||||
'notification email: link should contain the user login')
|
||||
|
||||
@mute_logger('openerp.addons.mail.mail_thread', 'openerp.osv.orm')
|
||||
def test_21_inbox_redirection(self):
|
||||
""" Tests designed to test the inbox redirection of emails notification URLs. """
|
||||
cr, uid, user_admin, group_pigs = self.cr, self.uid, self.user_admin, self.group_pigs
|
||||
model, act_id = self.ir_model_data.get_object_reference(cr, uid, 'mail', 'action_mail_inbox_feeds')
|
||||
model, port_act_id = self.ir_model_data.get_object_reference(cr, uid, 'portal', 'action_mail_inbox_feeds_portal')
|
||||
# Data: post a message on pigs
|
||||
msg_id = self.group_pigs.message_post(body='My body', partner_ids=[self.partner_bert_id, self.partner_chell_id], type='comment', subtype='mail.mt_comment')
|
||||
|
||||
# No specific parameters -> should redirect to Inbox
|
||||
action = self.mail_thread.message_redirect_action(cr, self.user_raoul_id, {'params': {}})
|
||||
self.assertEqual(action.get('type'), 'ir.actions.client',
|
||||
'URL redirection: action without parameters should redirect to client action Inbox')
|
||||
self.assertEqual(action.get('id'), act_id,
|
||||
'URL redirection: action without parameters should redirect to client action Inbox')
|
||||
|
||||
# Bert has read access to Pigs -> should redirect to form view of Pigs
|
||||
action = self.mail_thread.message_redirect_action(cr, self.user_raoul_id, {'params': {'message_id': msg_id}})
|
||||
self.assertEqual(action.get('type'), 'ir.actions.act_window',
|
||||
'URL redirection: action with message_id for read-accredited user should redirect to Pigs')
|
||||
self.assertEqual(action.get('res_id'), group_pigs.id,
|
||||
'URL redirection: action with message_id for read-accredited user should redirect to Pigs')
|
||||
|
||||
# Bert has no read access to Pigs -> should redirect to Inbox
|
||||
action = self.mail_thread.message_redirect_action(cr, self.user_bert_id, {'params': {'message_id': msg_id}})
|
||||
self.assertEqual(action.get('type'), 'ir.actions.client',
|
||||
'URL redirection: action without parameters should redirect to client action Inbox')
|
||||
self.assertEqual(action.get('id'), act_id,
|
||||
'URL redirection: action without parameters should redirect to client action Inbox')
|
||||
|
||||
# Chell has no read access to pigs -> should redirect to Portal Inbox
|
||||
action = self.mail_thread.message_redirect_action(cr, self.user_chell_id, {'params': {'message_id': msg_id}})
|
||||
self.assertEqual(action.get('type'), 'ir.actions.client',
|
||||
'URL redirection: action without parameters should redirect to client action Inbox')
|
||||
self.assertEqual(action.get('id'), port_act_id,
|
||||
'URL redirection: action without parameters should redirect to client action Inbox')
|
||||
|
||||
|
||||
Reference in New Issue
Block a user