summaryrefslogtreecommitdiff
path: root/addons/mail
diff options
context:
space:
mode:
authorThibault Delavallée <tde@openerp.com>2013-10-28 17:33:21 +0100
committerThibault Delavallée <tde@openerp.com>2013-10-28 17:33:21 +0100
commit5bb4fa2b4347a99b5c1a5722d5591c06f7032d4c (patch)
treeba5127daf27cc553ebc8683a39b68ebec379f4e9 /addons/mail
parent0db0f20bda410bd6601c266026363fc95b21c9c4 (diff)
parenta7ff75f94a168e26b9e9a208167b07d45dc751cb (diff)
[MERGE] Sync with trunk
bzr revid: tde@openerp.com-20131028163321-5o81wa1m7rzdp1dz
Diffstat (limited to 'addons/mail')
-rw-r--r--addons/mail/controllers/main.py9
-rw-r--r--addons/mail/mail_mail.py6
-rw-r--r--addons/mail/mail_thread.py44
-rw-r--r--addons/mail/static/src/js/mail_followers.js2
-rw-r--r--addons/mail/tests/test_mail_features.py108
-rw-r--r--addons/mail/update.py31
-rw-r--r--addons/mail/wizard/mail_compose_message_view.xml11
7 files changed, 151 insertions, 60 deletions
diff --git a/addons/mail/controllers/main.py b/addons/mail/controllers/main.py
index 959877ad098..c2e15c4a12f 100644
--- a/addons/mail/controllers/main.py
+++ b/addons/mail/controllers/main.py
@@ -3,15 +3,16 @@ import psycopg2
import openerp
from openerp import SUPERUSER_ID
-import openerp.addons.web.http as http
+from openerp import http
from openerp.addons.web.controllers.main import content_disposition
class MailController(http.Controller):
_cp_path = '/mail'
- @http.httprequest
+ @http.route('/mail/download_attachment', type='http', auth='user')
def download_attachment(self, req, model, id, method, attachment_id, **kw):
+ # FIXME use /web/binary/saveas directly
Model = req.session.model(model)
res = getattr(Model, method)(int(id), int(attachment_id))
if res:
@@ -20,10 +21,10 @@ class MailController(http.Controller):
if filecontent and filename:
return req.make_response(filecontent,
headers=[('Content-Type', 'application/octet-stream'),
- ('Content-Disposition', content_disposition(filename, req))])
+ ('Content-Disposition', content_disposition(filename))])
return req.not_found()
- @http.jsonrequest
+ @http.route('/mail/receive', type='json', auth='none')
def receive(self, req):
""" End-point to receive mail from an external SMTP server. """
dbs = req.jsonrequest.get('databases')
diff --git a/addons/mail/mail_mail.py b/addons/mail/mail_mail.py
index 91799b0ac63..8e99655dddb 100644
--- a/addons/mail/mail_mail.py
+++ b/addons/mail/mail_mail.py
@@ -157,9 +157,9 @@ class mail_mail(osv.Model):
'action': 'mail.action_mail_redirect',
}
if mail.notification:
- fragment.update({
- 'message_id': mail.mail_message_id.id,
- })
+ fragment['message_id'] = mail.mail_message_id.id
+ elif mail.model and mail.res_id:
+ fragment.update(model=mail.model, res_id=mail.res_id)
url = urljoin(base_url, "?%s#%s" % (urlencode(query), urlencode(fragment)))
return _("""<small>Access your messages and documents <a style='color:inherit' href="%s">in OpenERP</a></small>""") % url
else:
diff --git a/addons/mail/mail_thread.py b/addons/mail/mail_thread.py
index d72c24f6a99..9692b94f159 100644
--- a/addons/mail/mail_thread.py
+++ b/addons/mail/mail_thread.py
@@ -566,29 +566,37 @@ class mail_thread(osv.AbstractModel):
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._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
- msg_id = context.get('params', {}).get('message_id')
- if not msg_id:
+ params = context.get('params')
+ msg_id = model = res_id = None
+
+ if params:
+ msg_id = params.get('message_id')
+ model = params.get('model')
+ res_id = params.get('res_id')
+ if not msg_id and not (model and res_id):
return action
- msg = self.pool.get('mail.message').browse(cr, uid, msg_id, context=context)
- if msg.model and msg.res_id:
- action.update({
- 'context': {
- 'search_default_model': msg.model,
- 'search_default_res_id': msg.res_id,
- }
- })
- if self.pool.get(msg.model).check_access_rights(cr, uid, 'read', raise_exception=False):
+ if msg_id and not (model and res_id):
+ msg = self.pool.get('mail.message').browse(cr, uid, msg_id, context=context)
+ model, res_id = msg.model, msg.res_id
+
+ # if model + res_id found: try to redirect to the document or fallback on the Inbox
+ if model and res_id:
+ model_obj = self.pool.get(model)
+ if model_obj.check_access_rights(cr, uid, 'read', raise_exception=False):
try:
- model_obj = self.pool.get(msg.model)
- model_obj.check_access_rule(cr, uid, [msg.res_id], 'read', context=context)
+ model_obj.check_access_rule(cr, uid, [res_id], 'read', context=context)
if not hasattr(model_obj, '_get_formview_action'):
- action = self.pool.get('mail.thread')._get_formview_action(cr, uid, msg.res_id, model=msg.model, context=context)
+ action = self.pool.get('mail.thread')._get_formview_action(cr, uid, res_id, model=model, context=context)
else:
- action = model_obj._get_formview_action(cr, uid, msg.res_id, context=context)
+ action = model_obj._get_formview_action(cr, uid, res_id, context=context)
except (osv.except_osv, orm.except_orm):
pass
+ action.update({
+ 'context': {
+ 'search_default_model': model,
+ 'search_default_res_id': res_id,
+ }
+ })
return action
#------------------------------------------------------
@@ -1175,7 +1183,7 @@ class mail_thread(osv.AbstractModel):
# get partner info from email
partner_info = self.message_partner_info_from_emails(cr, uid, obj.id, [email], context=context)[0]
if partner_info.get('partner_id'):
- partner = self.pool.get('res.partner').browse(cr, SUPERUSER_ID, [partner_info.get('partner_id')], context=context)[0]
+ partner = self.pool.get('res.partner').browse(cr, SUPERUSER_ID, [partner_info['partner_id']], context=context)[0]
if email and email in [val[1] for val in result[obj.id]]: # already existing email -> skip
return result
if partner and partner in obj.message_follower_ids: # recipient already in the followers -> skip
diff --git a/addons/mail/static/src/js/mail_followers.js b/addons/mail/static/src/js/mail_followers.js
index a0dad1fcdbc..53cab629d79 100644
--- a/addons/mail/static/src/js/mail_followers.js
+++ b/addons/mail/static/src/js/mail_followers.js
@@ -151,7 +151,7 @@ openerp_mail_followers = function(session, mail) {
},
fetch_followers: function (value_) {
- this.value = value_ || {};
+ this.value = value_ || [];
return this.ds_model.call('read_followers_data', [this.value])
.then(this.proxy('display_followers'), this.proxy('fetch_generic'))
.then(this.proxy('display_buttons'))
diff --git a/addons/mail/tests/test_mail_features.py b/addons/mail/tests/test_mail_features.py
index 0688bf02606..62c76db5a40 100644
--- a/addons/mail/tests/test_mail_features.py
+++ b/addons/mail/tests/test_mail_features.py
@@ -231,6 +231,8 @@ class test_mail(TestMail):
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
+ # Test URL formatting
+ base_url = self.registry('ir.config_parameter').get_param(cr, uid, 'web.base.url')
# Partner data
partner_raoul = self.res_partner.browse(cr, uid, self.partner_raoul_id)
@@ -243,19 +245,59 @@ class test_mail(TestMail):
# 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')
+ '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')
+ '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(base_url, url,
+ 'notification email: link should contain web.base.url')
+ self.assertIn('db=%s' % cr.dbname, url,
+ 'notification email: link should contain database name')
self.assertIn('action=mail.action_mail_redirect', url,
- 'notification email: link should contain the redirect action')
+ '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')
+ 'notification email: link should contain the user login')
+
+ # Test: link for user -> with model and res_id
+ mail_mail_id = self.mail_mail.create(cr, uid, {'model': 'mail.group', 'res_id': group_pigs.id})
+ mail = self.mail_mail.browse(cr, uid, mail_mail_id)
+ url = mail_mail._get_partner_access_link(self.mail_mail, cr, uid, mail, partner=partner_raoul)
+ self.assertIn(base_url, url,
+ 'notification email: link should contain web.base.url')
+ self.assertIn('db=%s' % cr.dbname, url,
+ 'notification email: link should contain database name')
+ 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')
+ self.assertIn('model=mail.group', url,
+ 'notification email: link should contain the model when having not notification email on a record')
+ self.assertIn('res_id=%s' % group_pigs.id, url,
+ 'notification email: link should contain the res_id when having not notification email on a record')
+
+ # Test: link for user -> with model and res_id
+ mail_mail_id = self.mail_mail.create(cr, uid, {'notification': True, 'model': 'mail.group', 'res_id': group_pigs.id})
+ mail = self.mail_mail.browse(cr, uid, mail_mail_id)
+ url = mail_mail._get_partner_access_link(self.mail_mail, cr, uid, mail, partner=partner_raoul)
+ self.assertIn(base_url, url,
+ 'notification email: link should contain web.base.url')
+ self.assertIn('db=%s' % cr.dbname, url,
+ 'notification email: link should contain database name')
+ 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')
+ self.assertIn('message_id=%s' % mail.mail_message_id.id, url,
+ 'notification email: link based on message should contain the mail_message id')
+ self.assertNotIn('model', url,
+ 'notification email: link based on message should not contain model')
+ self.assertNotIn('res_id', url,
+ 'notification email: link based on message should not contain res_id')
@mute_logger('openerp.addons.mail.mail_thread', 'openerp.osv.orm')
def test_12_inbox_redirection(self):
@@ -267,24 +309,54 @@ class test_mail(TestMail):
# 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
+ 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'
+ )
+
+ # Raoul 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')
+ 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'
+ )
+ action = mail_thread.message_redirect_action(self.mail_thread, cr, self.user_raoul_id, {'params': {'model': 'mail.group', 'res_id': group_pigs.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')
+ 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'
+ )
+ action = mail_thread.message_redirect_action(self.mail_thread, cr, self.user_bert_id, {'params': {'model': 'mail.group', 'res_id': group_pigs.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. """
diff --git a/addons/mail/update.py b/addons/mail/update.py
index 94416aeb356..bcf9bb8c7c9 100644
--- a/addons/mail/update.py
+++ b/addons/mail/update.py
@@ -6,8 +6,8 @@ import urllib
import urllib2
import openerp
-from openerp import release
-from openerp.osv import fields, osv
+from openerp import release, SUPERUSER_ID
+from openerp.osv import osv
from openerp.tools.translate import _
from openerp.tools.safe_eval import safe_eval
from openerp.tools.config import config
@@ -86,25 +86,26 @@ class publisher_warranty_contract(osv.osv):
try:
try:
result = get_sys_logs(self, cr, uid)
- except Exception, ex:
+ except Exception:
if cron_mode: # we don't want to see any stack trace in cron
return False
_logger.debug("Exception while sending a get logs messages", exc_info=1)
raise osv.except_osv(_("Error"), _("Error during communication with the publisher warranty server."))
- limit_date = (datetime.datetime.now() - _PREVIOUS_LOG_CHECK).strftime(misc.DEFAULT_SERVER_DATETIME_FORMAT)
# old behavior based on res.log; now on mail.message, that is not necessarily installed
- proxy = self.pool.get('mail.message')
-
- model, res_id = self.pool.get('ir.model.data').get_object_reference(cr, uid, 'mail', 'group_all_employees')
-
+ IMD = self.pool['ir.model.data']
+ user = self.pool['res.users'].browse(cr, SUPERUSER_ID, SUPERUSER_ID)
+ try:
+ poster = IMD.get_object(cr, SUPERUSER_ID, 'mail', 'group_all_employees')
+ except ValueError:
+ # Cannot found group, post the message on the wall of the admin
+ poster = user
+ if not poster.exists():
+ return True
for message in result["messages"]:
- values = {
- 'body' : message,
- 'model' : 'mail.group',
- 'res_id' : res_id,
- 'user_id' : False,
- }
- proxy.create(cr, uid, values, context=context)
+ try:
+ poster.message_post(body=message, subtype='mt_comment', partner_ids=[user.partner_id.id])
+ except Exception:
+ _logger.warning('Cannot send ping message', exc_info=True)
except Exception:
if cron_mode:
return False # we don't want to see any stack trace in cron
diff --git a/addons/mail/wizard/mail_compose_message_view.xml b/addons/mail/wizard/mail_compose_message_view.xml
index 0c86bae7e5f..948d9b3832c 100644
--- a/addons/mail/wizard/mail_compose_message_view.xml
+++ b/addons/mail/wizard/mail_compose_message_view.xml
@@ -13,8 +13,17 @@
<field name="res_id" invisible="1"/>
<field name="parent_id" invisible="1"/>
<field name="mail_server_id" invisible="1"/>
+ <!-- Various warnings -->
<field name="use_active_domain" invisible="1"/>
- <field name="active_domain" invisible="1"/>
+ <div colspan="2" class="oe_form_box_info oe_text_center"
+ attrs="{'invisible': [('use_active_domain', '!=', True)]}">
+ <p>
+ <strong>All records matching your current search filter will be mailed,
+ not only the ids selected in the list view.</strong><br />
+ If you want to work only with selected ids, please uncheck the
+ list header checkbox.
+ </p>
+ </div>
<!-- visible wizard -->
<field name="email_from"
attrs="{'invisible':[('composition_mode', '!=', 'mass_mail')]}"/>