[FIX] [WIP] email_template: composition wizard: added render_message that get back the values generated by the template in mass_mail mode; email_template overrides the basic behavior of mail, to use the templating power (niak). Various fixes in the wizard, mostly in onchange_template_id. Some code cleaning. Updated the view, because onchange_template_id now take an extr argument (model). Added some tests used during this WIP. Will be updated next week.

bzr revid: tde@openerp.com-20120831171900-ii0ucshjnf8vjc3z
This commit is contained in:
Thibault Delavallée 2012-08-31 19:19:00 +02:00
parent 7eb5b82950
commit 761864c11c
3 changed files with 94 additions and 70 deletions

View File

@ -53,51 +53,59 @@ class test_message_compose(common.TransactionCase):
""" Tests designed for the mail.compose.message wizard updated by email_template. """ """ Tests designed for the mail.compose.message wizard updated by email_template. """
cr, uid = self.cr, self.uid cr, uid = self.cr, self.uid
mail_compose = self.registry('mail.compose.message') mail_compose = self.registry('mail.compose.message')
self.res_users.write(cr, uid, [uid], {'signature': 'Admin', 'email': 'a@a'}) self.res_users.write(cr, uid, [uid], {'signature': 'Admin', 'email': 'a@a.a'})
user_admin = self.res_users.browse(cr, uid, uid) user_admin = self.res_users.browse(cr, uid, uid)
group_model_id = self.registry('ir.model').search(cr, uid, [('model', '=', 'mail.group')])[0]
group_pigs = self.mail_group.browse(cr, uid, self.group_pigs_id) group_pigs = self.mail_group.browse(cr, uid, self.group_pigs_id)
group_bird_id = self.mail_group.create(cr, uid, {'name': 'Bird', 'description': 'I am angry !'})
group_bird = self.mail_group.browse(cr, uid, group_bird_id)
# Create template on mail.group # Create template on mail.group
group_model_id = self.registry('ir.model').search(cr, uid, [('model', '=', 'mail.group')])[0]
email_template = self.registry('email.template') email_template = self.registry('email.template')
email_template_id = email_template.create(cr, uid, {'model_id': group_model_id, email_template_id = email_template.create(cr, uid, {'model_id': group_model_id,
'name': 'Pigs Template', 'subject': '${record.name}', 'name': 'Pigs Template', 'subject': '${object.name}',
'body_html': '${object.description}', 'user_signature': True, 'body_html': '${object.description}', 'user_signature': True,
'email_to': 'b@b c@c', 'email_cc': 'd@d'}) 'email_to': 'b@b.b c@c.c', 'email_cc': 'd@d.d'})
# import pdb
# pdb.set_trace()
# Mail data # Mail data
_subject = 'Pigs' _subject1 = 'Pigs'
_body_text = 'Pigs rules' _subject2 = 'Bird'
_body_text1 = 'Pigs rules'
_body_text_html1 = 'Pigs rules<pre>Admin</pre>'
_body_text2 = 'I am angry !'
_body_text_html2 = 'I am angry !<pre>Admin</pre>'
# 3 - Create in mass_mail composition mode that should work with or without email_template installed # CASE1: create in mass_mail composition mode that should work with email_template installed
compose_id = mail_compose.create(cr, uid, compose_id = mail_compose.create(cr, uid,
{'subject': _subject, 'body': _body_text}, {'subject': 'Forget me subject', 'body': 'Dummy body'},
{'default_composition_mode': 'mass_mail', 'default_model': 'mail.group', {'default_composition_mode': 'mass_mail', 'default_model': 'mail.group',
'default_res_id': -1, 'default_use_template': True, 'default_res_id': -1, 'default_use_template': True,
'active_ids': [self.group_pigs_id], 'default_template_id': email_template_id}) 'active_ids': [self.group_pigs_id, group_bird_id], 'default_template_id': email_template_id})
compose = mail_compose.browse(cr, uid, compose_id) compose = mail_compose.browse(cr, uid, compose_id)
# print compose.subject # print compose.subject
# Try the 'onchange_template_id' # Try the 'onchange_template_id'
values = mail_compose.onchange_template_id(cr, uid, [], compose.use_template, compose.template_id, compose.composition_mode, compose.res_id) values = mail_compose.onchange_template_id(cr, uid, [], compose.use_template, compose.template_id, compose.composition_mode, compose.model, compose.res_id)
# print values print values
values = mail_compose.onchange_use_template(cr, uid, [], not compose.use_template, compose.template_id, compose.composition_mode, compose.res_id) # compose.write(values['value'])
# print values values = mail_compose.onchange_use_template(cr, uid, [], not compose.use_template, compose.template_id, compose.composition_mode, compose.model, compose.res_id)
print values
compose.refresh() compose.refresh()
# Post the comment, get created message
# # Post the comment, get created message mail_compose.send_mail(cr, uid, [compose_id], {'default_res_id': -1, 'active_ids': [self.group_pigs_id, group_bird_id]})
# mail_compose.send_mail(cr, uid, [compose_id], {'default_res_id': -1, 'active_ids': [self.group_pigs_id]}) group_pigs.refresh()
# group_pigs.refresh() group_bird.refresh()
# msg = group_pigs.message_ids[0] message_pigs = group_pigs.message_ids[0]
message_bird = group_bird.message_ids[0]
# # Test: last message on Pigs = last created message # Test: subject, body
# test_msg = self.mail_message.browse(cr, uid, self.mail_message.search(cr, uid, [], limit=1))[0] self.assertEqual(message_pigs.subject, _subject1, 'mail.message subject on Pigs incorrect')
# self.assertEqual(msg.id, test_msg.id, 'Pigs did not receive its mass mailing message') self.assertEqual(message_bird.subject, _subject2, 'mail.message subject on Bird incorrect')
# # Test: mail.message: subject, body self.assertEqual(message_pigs.body, _body_text_html1, 'mail.message body on Pigs incorrect')
# self.assertEqual(msg.subject, _subject, 'mail.message subject is incorrect') self.assertEqual(message_bird.body, _body_text_html2, 'mail.message body on Bird incorrect')
# self.assertEqual(msg.body, group_pigs.description, 'mail.message body is incorrect') # Test: partner_ids
print message_pigs.partner_ids
print message_pigs.partner_ids
self.assertEqual(len(message_pigs.partner_ids), 6, 'mail.message partner_ids incorrect')

View File

@ -27,13 +27,9 @@ from osv import fields
from tools.translate import _ from tools.translate import _
class mail_compose_message(osv.osv_memory): class mail_compose_message(osv.osv_memory):
""" Inherit mail_compose_message to add email template feature in the
message composer. """
_inherit = 'mail.compose.message' _inherit = 'mail.compose.message'
def _get_templates(self, cr, uid, context=None): def _get_templates(self, cr, uid, context=None):
""" Return Email Template of particular Model. """
if context is None: if context is None:
context = {} context = {}
model = False model = False
@ -52,7 +48,6 @@ class mail_compose_message(osv.osv_memory):
return [] return []
def default_get(self, cr, uid, fields, context=None): def default_get(self, cr, uid, fields, context=None):
""" Override to handle templates. """
if context is None: if context is None:
context = {} context = {}
result = super(mail_compose_message, self).default_get(cr, uid, fields, context=context) result = super(mail_compose_message, self).default_get(cr, uid, fields, context=context)
@ -65,39 +60,34 @@ class mail_compose_message(osv.osv_memory):
'template_id': fields.selection(_get_templates, 'Template', size=-1), 'template_id': fields.selection(_get_templates, 'Template', size=-1),
} }
def onchange_template_id(self, cr, uid, ids, use_template, template_id, composition_mode, res_id, context=None): def onchange_template_id(self, cr, uid, ids, use_template, template_id, composition_mode, model, res_id, context=None):
""" onchange_template_id: read or render the template if set, get back """ - use_template not set: return default_get
to default values if not. """ - use_template set:
- mass_mailing: we cannot render, so return the template values
- else: return rendered values """
fields = ['body', 'body_html', 'subject', 'partner_ids', 'email_to', 'email_cc'] fields = ['body', 'body_html', 'subject', 'partner_ids', 'email_to', 'email_cc']
if use_template and template_id: if use_template and template_id and composition_mode == 'mass_mail':
# use the original template values, to be rendered when actually sent values = self.pool.get('email.template').read(cr, uid, template_id, fields, context)
if composition_mode == 'mass_mail': elif use_template and template_id:
values = self.pool.get('email.template').read(cr, uid, template_id, fields, context) values = self.pool.get('email.template').generate_email(cr, uid, template_id, res_id, context=context)
# render the mail as one-shot
else: values['attachment_ids'] = []
values = self.pool.get('email.template').generate_email(cr, uid, template_id, res_id, context=context) attachment_obj = self.pool.get('ir.attachment')
# retrofit generated attachments in the expected field format for attach_fname, attach_datas in values.get('attachments', []):
if values['attachments']: data_attach = {
attachment = values.pop('attachments') 'name': attach_fname,
attachment_obj = self.pool.get('ir.attachment') 'datas': attach_datas,
att_ids = [] 'datas_fname': attach_fname,
for fname, fcontent in attachment.iteritems(): 'description': fname,
data_attach = { 'res_model': model,
'name': fname, 'res_id': res_id,
'datas': fcontent, }
'datas_fname': fname, values['attachment_ids'].append(attachment_obj.create(cr, uid, data_attach), context=context)
'description': fname, else:
'res_model' : self._name,
'res_id' : ids[0] if ids else False
}
att_ids.append(attachment_obj.create(cr, uid, data_attach))
values['attachment_ids'] = att_ids
else: # restore defaults
values = self.default_get(cr, uid, fields, context=context) values = self.default_get(cr, uid, fields, context=context)
if values.get('body_html') and not values.get('body'): if values.get('body_html') and not values.get('body'):
values['body'] = values.get('body_html') values['body'] = values.get('body_html')
values.update(use_template=use_template, template_id=template_id) values.update(use_template=use_template, template_id=template_id)
return {'value': values} return {'value': values}
@ -107,16 +97,15 @@ class mail_compose_message(osv.osv_memory):
emulate an on_change, then writes the value to update the form. """ emulate an on_change, then writes the value to update the form. """
for record in self.browse(cr, uid, ids, context=context): for record in self.browse(cr, uid, ids, context=context):
onchange_res = self.onchange_use_template(cr, uid, ids, not record.use_template, onchange_res = self.onchange_use_template(cr, uid, ids, not record.use_template,
record.template_id, record.composition_mode, record.res_id, context=context)['value'] record.template_id, record.composition_mode, record.model, record.res_id, context=context)['value']
record.write(onchange_res) record.write(onchange_res)
return True return True
def onchange_use_template(self, cr, uid, ids, use_template, template_id, composition_mode, res_id, context=None): def onchange_use_template(self, cr, uid, ids, use_template, template_id, composition_mode, model, res_id, context=None):
""" onchange_use_template (values: True or False). If use_template is """ onchange_use_template (values: True or False). If use_template is
False, we do like an onchange with template_id False for values """ False, we do like an onchange with template_id False for values """
onchange_template_values = self.onchange_template_id(cr, uid, ids, use_template, return self.onchange_template_id(cr, uid, ids, use_template,
template_id, composition_mode, res_id, context=context) template_id, composition_mode, model, res_id, context=context)
return onchange_template_values
def save_as_template(self, cr, uid, ids, context=None): def save_as_template(self, cr, uid, ids, context=None):
""" hit save as template button: current form value will be a new """ hit save as template button: current form value will be a new
@ -142,9 +131,36 @@ class mail_compose_message(osv.osv_memory):
record.write({'template_id': template_id, 'use_template': True}) record.write({'template_id': template_id, 'use_template': True})
return True return True
#------------------------------------------------------
# Wizard validation and send
#------------------------------------------------------
def render_message(self, cr, uid, wizard, model, res_id, context=None):
""" Generate an email from the template for given (model, res_id) pair.
This method is meant to be inherited by email_template that will
produce a more complete dictionary, with email_to, ...
"""
# render the template to get the email
template_values = self.pool.get('email.template').generate_email(cr, uid, wizard.template_id, res_id, context=context)
# TDE TODO: handle fields to update / not to update (mail_server_id, auto_delete, ...)
# transform email_to, email_cc into partner_ids
partner_ids = []
mails = tools.email_split(template_values.pop('email_to', '') + ' ' + template_values.pop('email_cc', ''))
for mail in mails:
partner_search_ids = self.pool.get('res.partner').search(cr, uid, [('email', 'ilike', mail)], context=context)
if partner_search_ids:
partner_ids.append((4, partner_search_ids[0]))
else:
partner_id = self.pool.get('res.partner').name_create(cr, uid, mail, context=context)[0]
partner = self.pool.get('res.partner').browse(cr, uid, partner_id, context=context)
partner_ids.append((4, partner_id))
# get values to return
email_dict = super(mail_compose_message, self).render_message(cr, uid, wizard, model, res_id, context)
email_dict.update(template_values)
email_dict.update(partner_ids=partner_ids, attachments=template_values.get('attachments'))
return email_dict
def render_template(self, cr, uid, template, model, res_id, context=None): def render_template(self, cr, uid, template, model, res_id, context=None):
""" Override of mail.compose.message behavior: use the power of
templates ! """
return self.pool.get('email.template').render_template(cr, uid, template, model, res_id, context=context) return self.pool.get('email.template').render_template(cr, uid, template, model, res_id, context=context)
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: # vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:

View File

@ -19,7 +19,7 @@
<group attrs="{'invisible':[('use_template','=',False)]}" colspan="4" col="4"> <group attrs="{'invisible':[('use_template','=',False)]}" colspan="4" col="4">
<field name="use_template" invisible="1"/> <field name="use_template" invisible="1"/>
<field name="template_id" colspan="3" <field name="template_id" colspan="3"
on_change="onchange_template_id(use_template, template_id, composition_mode, res_id, context)"/> on_change="onchange_template_id(use_template, template_id, composition_mode, model, res_id, context)"/>
</group> </group>
</xpath> </xpath>
</data> </data>
@ -34,10 +34,10 @@
<data> <data>
<xpath expr="//field[@name='partner_ids']" position="after"> <xpath expr="//field[@name='partner_ids']" position="after">
<field name="use_template" colspan="2" nolabel="1" invisible="1" <field name="use_template" colspan="2" nolabel="1" invisible="1"
on_change="onchange_use_template(use_template, template_id, composition_mode, res_id, context)"/> on_change="onchange_use_template(use_template, template_id, composition_mode, model, res_id, context)"/>
<field name="template_id" colspan="2" nolabel="1" <field name="template_id" colspan="2" nolabel="1"
attrs="{'invisible':[('use_template','=',False)]}" attrs="{'invisible':[('use_template','=',False)]}"
on_change="onchange_template_id(use_template, template_id, composition_mode, res_id, context)"/> on_change="onchange_template_id(use_template, template_id, composition_mode, model, res_id, context)"/>
</xpath> </xpath>
<xpath expr="//button[@class='oe_mail_compose_message_attachment']" position="before"> <xpath expr="//button[@class='oe_mail_compose_message_attachment']" position="before">
<button icon="/email_template/static/src/img/email_template.png" <button icon="/email_template/static/src/img/email_template.png"