Files
odoo_source/addons/website_version/models/ir_ui_view.py
T
Nicolas Lempereur b0b6b9afb5 [FIX] website{,_version}: get current version view
customize_template_get which gets template inheritence informations was
not taken into account by website version, so at one time we could get
an erroneous view version instead of the wanted one.

This commit refactor some of the code adding a function to sort view and
find the most suitable one (based on website and version in request).

This function is then used in ir.ui.view `_view_obj`'s function to
select the correct view.

related to opw-667225
2016-03-08 17:13:58 +01:00

166 lines
7.3 KiB
Python

# -*- coding: utf-8 -*-
from lxml import etree
from openerp import tools, fields, models, api
class view(models.Model):
_inherit = "ir.ui.view"
version_id = fields.Many2one('website_version.version', ondelete='cascade', string="Version")
def _sort_suitability_key(self):
"""
Key function to sort views by descending suitability
Suitability of a view is defined as follow:
* if the view and request version are matched,
* then fallback on previously defined suitability
"""
original_suitability = super(view, self)._sort_suitability_key()
context_version_id = self.env.context.get('version_id', 0)
different_version = context_version_id != (self.version_id.id or 0)
return (different_version, original_suitability)
@api.multi
def write(self, vals):
if self.env.context is None:
self.env.context = {}
version_id = self.env.context.get('version_id')
#If you write on a shared view, your modifications will be seen on every website wich uses these view.
#To dedicate a view for a specific website, you must create a version and publish these version.
if version_id and not self.env.context.get('write_on_view') and not 'active' in vals:
self.env.context = dict(self.env.context, write_on_view=True)
version = self.env['website_version.version'].browse(version_id)
website_id = version.website_id.id
version_view_ids = self.env['ir.ui.view']
for current in self:
#check if current is in version
if current.version_id.id == version_id:
version_view_ids += current
else:
new_v = self.search([('website_id', '=', website_id), ('version_id', '=', version_id), ('key', '=', current.key)])
if new_v:
version_view_ids += new_v
else:
copy_v = current.copy({'version_id': version_id, 'website_id': website_id})
version_view_ids += copy_v
return super(view, version_view_ids).write(vals)
else:
self.env.context = dict(self.env.context, write_on_view=True)
return super(view, self).write(vals)
@api.one
def publish(self):
#To delete and replace views which are in the website( in fact with website_id)
master_record = self.search([('key', '=', self.key), ('version_id', '=', False), ('website_id', '=', self.website_id.id)])
if master_record:
master_record.unlink()
self.copy({'version_id': None})
#To publish a view in backend
@api.multi
def action_publish(self):
self.publish()
@api.model
def get_view_id(self, xml_id):
if self.env.context and 'website_id' in self.env.context and not isinstance(xml_id, (int, long)):
domain = [('key', '=', xml_id), '|', ('website_id', '=', self.env.context['website_id']), ('website_id', '=', False)]
if 'version_id' in self.env.context:
domain += ['|', ('version_id', '=', self.env.context['version_id']), ('version_id', '=', False)]
xml_id = self.search(domain, order='website_id,version_id', limit=1).id
else:
xml_id = super(view, self).get_view_id(xml_id)
return xml_id
@tools.ormcache_context(**dict(accepted_keys=('lang', 'inherit_branding', 'editable', 'translatable', 'website_id', 'version_id')))
def _read_template(self, cr, uid, view_id, context=None):
arch = self.read_combined(cr, uid, view_id, fields=['arch'], context=context)['arch']
arch_tree = etree.fromstring(arch)
if 'lang' in context:
arch_tree = self.translate_qweb(cr, uid, view_id, arch_tree, context['lang'], context)
self.distribute_branding(arch_tree)
root = etree.Element('templates')
root.append(arch_tree)
arch = etree.tostring(root, encoding='utf-8', xml_declaration=True)
return arch
#To take the right inheriting views
@api.model
def get_inheriting_views_arch(self, view_id, model):
arch = super(view, self).get_inheriting_views_arch(view_id, model)
vw = self.browse(view_id)
if not (self.env.context and self.env.context.get('website_id') and vw.type == 'qweb'):
return arch
# keep the most suited view when several view with same key are available
chosen_view_ids = self.browse(view_id for _, view_id in arch).filter_duplicate().ids
return [x for x in arch if x[1] in chosen_view_ids]
#To active or desactive the right views according to the key
def toggle(self, cr, uid, ids, context=None):
""" Switches between enabled and disabled statuses
"""
for view in self.browse(cr, uid, ids, context=dict(context or {}, active_test=False)):
all_id = self.search(cr, uid, [('key', '=', view.key)], context=dict(context or {}, active_test=False))
for v in self.browse(cr, uid, all_id, context=dict(context or {}, active_test=False)):
v.write({'active': not v.active})
@api.model
def translate_qweb(self, id_, arch, lang):
view = self.browse(id_)
if not view.key:
return super(view, self).translate_qweb(id_, arch, lang)
views = self.search([('key', '=', view.key), '|',
('website_id', '=', view.website_id.id), ('website_id', '=', False)])
fallback_views = self
for v in views:
if v.mode == 'primary' and v.inherit_id.mode == 'primary':
# template is `cloned` from parent view
fallback_views += view.inherit_id
views += fallback_views
def translate_func(term):
Translations = self.env['ir.translation']
trans = Translations._get_source('website', 'view', lang, term, views.ids)
return trans
self._translate_qweb(arch, translate_func)
return arch
@api.model
def customize_template_get(self, key, full=False, bundles=False, **kw):
result = super(view, self).customize_template_get(key, full=full, bundles=bundles, **kw)
check = []
res = []
for data in result:
if data['name'] not in check:
check.append(data['name'])
res.append(data)
return res
@api.model
def get_view_translations(self, xml_id, lang,
field=['id', 'res_id', 'value', 'state', 'gengo_translation']):
irt = self.pool['ir.translation']
view = self.browse(xml_id)
view_list = self.search([('key', '=', view.key),
'|', ('website_id', '=', view.website_id.id), ('website_id', '=', False)])
views_ids = []
for v in view_list:
views = self.customize_template_get(v.id, full=True)
views_ids += [v.get('id') for v in views if v.get('active')]
domain = [('type', '=', 'view'), ('res_id', 'in', views_ids), ('lang', '=', lang)]
element_list = irt.search_read(self.env.cr, self.env.uid,
domain, field, context=self.env.context)
for element in element_list:
if element['res_id'] in view_list.ids:
element['res_id'] = xml_id
return element_list